From 658b76f306463fb75b9ac5f288b52387bbe1568f Mon Sep 17 00:00:00 2001
From: mage2-team <mage2-team@magento.com>
Date: Mon, 16 Jun 2014 04:10:07 -0700
Subject: [PATCH] 2.0.0.0-dev82 * Added support for MTF Reporting Tool *
 Framework improvements:   * Covered the following Magento application
 components with unit tests:       * `ConfigurableProduct/Helper/Data.php`    
   * `ConfigurableProduct/Model/Export/RowCustomizer.php`       *
 `ConfigurableProduct/Model/Product/Type/Configurable.php`       *
 `ConfigurableProduct/Model/Product/Type/Plugin.php`       *
 `ConfigurableProduct/Model/Quote/Item/QuantityValidator/Initializer/Option/Plugin/ConfigurableProduct.php`
       * `CatalogSearch/Helper/Data.php`   * Covered Magento lib with unit
 tests:       * `lib/internal/Magento/Framework/DB/Helper/AbstractHelper.php` 
      * `lib/internal/Magento/Framework/DB/Tree/Node.php` * Created Service
 API for Magento_Catalog Module:   * Implemented the Product API   *
 Implemented the ProductAttributeRead API * Fixed bugs:   * Fixed issues with
 form elements visibility on the backend   * Fixed an issue where backend
 forms contained an excessive container   * Fixed an issue where a wrong
 category structure was displayed on the Category page   * Fixed an issue
 where the pub/index.php entry point was broken because of the obsolete
 constants   * Fixed an issue where it was impossible to pass an empty array
 as an argument in DI configuration and layout updates   * Fixed an issue with
 status and visibility settings of a related product on the backend   * Fixed
 an issue with unused DB indexes, which used resources, but did not contribute
 to higher performance   * Fixed an issue where it was possible to create a
 downloadable product without specifying a link or a file   * Fixed an issue
 where a fatal error occured when opening a fixed bundle product with custom
 options page on the frontend   * Fixed an issue where the was a wrong config
 key for backend cataloginventory * Processed GitHub requests:   * [#548]
 (https://github.com/magento/magento2/issues/548) -- Console installer doesn't
 checks filesystem permissions   * [#552]
 (https://github.com/magento/magento2/issues/552) -- backend notifications
 sitebuild bug   * [#562] (https://github.com/magento/magento2/pull/562) --
 Bugfix Magento\Framework\DB\Adapter\Pdo\Mysql::getCreateTable()   * [#565]
 (https://github.com/magento/magento2/pull/565) --
 Magento\CatalogSearch\Model\Query::getResultCollection() not working   *
 [#557] (https://github.com/magento/magento2/issues/557) -- translation
 anomalies backend login page * Added the following functional tests:   *
 Advanced Search   * Existing Customer Creation   * Product Attribute Creation
   * Product Rating Creation   * Sales Rule Creation   * System Product
 Attribute Deletion   * Tax Rate Creation   * Tax Rule Deletion   * Update
 Category   * Update Category Url Rewrite   * Update Product Url Rewrite

---
 CHANGELOG.md                                  |   47 +
 .../AdminNotification/Block/ToolbarEntry.php  |    7 +-
 .../Backend/Block/Widget/Grid/Extended.php    |   69 +-
 .../Backend/view/adminhtml/layout/default.xml |    2 +-
 .../adminhtml/templates/admin/login.phtml     |    4 +-
 .../Bundle/Model/Plugin/PriceBackend.php      |   51 +
 app/code/Magento/Bundle/etc/adminhtml/di.xml  |    3 +
 app/code/Magento/Bundle/etc/di.xml            |    1 +
 .../Edit/Action/Attribute/Tab/Inventory.php   |   14 +-
 .../Adminhtml/Product/Edit/Tab/Inventory.php  |   21 +-
 .../Catalog/Block/Product/AbstractProduct.php |   48 +-
 .../Magento/Catalog/Block/Product/Context.php |   21 +-
 .../Magento/Catalog/Block/Product/View.php    |   12 +-
 .../Adminhtml/Product/Action/Attribute.php    |   50 +-
 .../Model/Product/Attribute/Backend/Sku.php   |    4 +-
 .../Model/Product/Attribute/Backend/Stock.php |    9 +-
 .../Model/Product/Type/AbstractType.php       |   84 +-
 .../Catalog/Model/Product/Type/Simple.php     |    5 +-
 .../Product/Link/Product/Collection.php       |    1 +
 .../Catalog/Service/V1/Data/Converter.php     |   85 +
 .../Service/V1/Data/Eav/AttributeMetadata.php |  393 ++
 .../V1/Data/Eav/AttributeMetadataBuilder.php  |  441 ++
 .../Catalog/Service/V1/Data/Eav/Option.php    |   59 +
 .../Service/V1/Data/Eav/OptionBuilder.php     |   52 +
 .../Service/V1/Data/Eav/ValidationRule.php    |   54 +
 .../V1/Data/Eav/ValidationRuleBuilder.php     |   49 +
 .../Catalog/Service/V1/Data/Product.php       |  155 +
 .../Service/V1/Data/ProductAttributeType.php  |   58 +
 .../V1/Data/ProductAttributeTypeBuilder.php   |   53 +
 .../Service/V1/Data/ProductBuilder.php        |  207 +
 .../Catalog/Service/V1/Data/ProductMapper.php |   71 +
 .../Catalog/Service/V1/Data/SearchResults.php |   61 +
 .../Service/V1/Data/SearchResultsBuilder.php  |   68 +
 .../Service/V1/Product/Link/ReadService.php   |    1 +
 .../Service/V1/Product/Link/WriteService.php  |    1 +
 .../V1/Product/{Link => }/ProductLoader.php   |    9 +-
 .../V1/ProductAttributeReadService.php        |   88 +
 .../ProductAttributeReadServiceInterface.php  |   50 +
 .../Service/V1/ProductMetadataService.php     |  201 +
 .../V1/ProductMetadataServiceInterface.php    |   73 +
 .../Catalog/Service/V1/ProductService.php     |  269 ++
 .../Service/V1/ProductServiceInterface.php    |   81 +
 app/code/Magento/Catalog/etc/di.xml           |    3 +
 app/code/Magento/Catalog/etc/webapi.xml       |   42 +
 .../sql/catalog_setup/install-1.6.0.0.0.php   |   66 -
 .../sql/catalog_setup/install-1.6.0.0.php     | 3993 -----------------
 .../upgrade-1.6.0.0.7-1.6.0.0.8.php           |    6 -
 .../upgrade-1.6.0.0.9-1.6.0.0.10.php          |    3 -
 .../product/edit/options/type/file.phtml      |    4 +-
 .../CatalogInventory/Block/Qtyincrements.php  |   21 +-
 .../Block/Stockqty/AbstractStockqty.php       |   41 +-
 .../Block/Stockqty/Composite.php              |   20 +-
 .../Block/Stockqty/DefaultStockqty.php        |    5 +-
 .../Block/Stockqty/Type/Grouped.php           |    9 +-
 .../Magento/CatalogInventory/Helper/Data.php  |   90 +-
 .../CatalogInventory/Helper/Minsaleqty.php    |   44 +-
 .../Model/Config/Backend/Managestock.php      |    7 +-
 .../CatalogInventory/Model/Indexer/Stock.php  |   21 +-
 .../CatalogInventory/Model/Observer.php       |  132 +-
 .../CopyConstructor/CatalogInventory.php      |    3 +-
 .../Model/Resource/Indexer/Stock.php          |   65 +-
 .../Resource/Indexer/Stock/DefaultStock.php   |   22 +-
 .../CatalogInventory/Model/Resource/Stock.php |   84 +-
 .../Model/Resource/Stock/Item.php             |   16 +-
 .../Model/Resource/Stock/Status.php           |   46 +-
 .../Model/Source/Backorders.php               |    3 +
 .../CatalogInventory/Model/Source/Stock.php   |    5 +-
 .../Magento/CatalogInventory/Model/Stock.php  |   52 +-
 .../CatalogInventory/Model/Stock/Item.php     |  336 +-
 .../Model/Stock/ItemRegistry.php              |   74 +
 .../CatalogInventory/Model/Stock/Status.php   |  153 +-
 .../Model/System/Config/Backend/Minqty.php    |   10 +-
 .../System/Config/Backend/Minsaleqty.php      |    4 +-
 .../System/Config/Backend/Qtyincrements.php   |    8 +-
 .../Service/V1/Data/StockItem.php             |  286 ++
 .../Service/V1/Data/StockItemBuilder.php      |   33 +
 .../CatalogInventory/Service/V1/StockItem.php |  340 ++
 .../Service/V1/StockItemInterface.php         |  184 +
 .../Service/V1/StockStatusService.php         |   54 +
 .../V1/StockStatusServiceInterface.php        |   42 +
 app/code/Magento/CatalogInventory/etc/di.xml  |    1 +
 .../Magento/CatalogInventory/etc/module.xml   |    1 -
 .../install-1.6.0.0.php                       |    3 -
 .../sql/catalogrule_setup/install-1.6.0.0.php |    6 -
 .../upgrade-1.6.0.1-1.6.0.2.php               |    6 -
 .../Model/Resource/Advanced/Collection.php    |    2 +-
 .../Model/Resource/Search/Collection.php      |    2 +-
 .../catalogsearch_setup/install-1.6.0.0.php   |    3 -
 app/code/Magento/Checkout/Block/Success.php   |    2 +-
 app/code/Magento/Checkout/Model/Cart.php      |   99 +-
 .../Block/Stockqty/Type/Configurable.php      |    5 +-
 .../Model/Product/Type/Configurable.php       |   14 +-
 .../configurable_setup/install-1.0.0.0.php    |   12 -
 .../catalog/product/edit/super/config.phtml   |    2 +-
 .../view/adminhtml/web/product/product.css    |    6 +
 .../Core/sql/core_setup/install-1.6.0.0.php   |    3 -
 .../sql/customer_setup/install-1.6.0.0.php    |   30 -
 .../downloadable_setup/install-1.6.0.0.php    |    9 -
 .../product/edit/downloadable/links.phtml     |    4 +-
 .../adminhtml/web/product/validation-rules.js |   22 +-
 .../Attribute/Backend/AbstractBackend.php     |   19 +-
 .../Eav/sql/eav_setup/install-1.6.0.0.php     |   57 -
 .../googleoptimizer_setup/install-2.0.0.0.php |    3 -
 .../Block/Stockqty/Type/Grouped.php           |   10 +-
 .../Model/Import/Entity/Product.php           |   18 +-
 .../Install/Model/Installer/Console.php       |   31 +-
 .../sql/newsletter_setup/install-1.6.0.0.php  |    3 -
 .../Payment/Model/Method/AbstractMethod.php   |   17 +
 .../Controller/Express/AbstractExpress.php    |    1 +
 .../Magento/Reports/Model/Resource/Event.php  |   63 +-
 .../Resource/Product/Lowstock/Collection.php  |   16 +-
 .../Adminhtml/Order/Create/Items/Grid.php     |    1 -
 .../Sales/sql/sales_setup/install-1.6.0.0.php |    3 -
 .../sql/salesrule_setup/install-1.6.0.0.php   |    6 -
 .../upgrade-1.6.0.2-1.6.0.3.php               |    6 -
 .../Tax/sql/tax_setup/install-1.6.0.0.php     |   10 +-
 .../sql/tax_setup/upgrade-1.6.0.1-1.6.0.2.php |    3 -
 .../view/frontend/layout/page_calendar.xml    |    2 +-
 .../sql/translation_setup/install-1.0.0.0.php |    3 -
 .../sql/urlrewrite_setup/install-1.0.0.0.php  |    3 -
 .../Magento/Webapi/Controller/Rest/Router.php |    6 +-
 .../Controller/ServiceArgsSerializer.php      |    2 +-
 app/code/Magento/Webapi/Model/Rest/Config.php |    4 +-
 .../sql/widget_setup/install-1.6.0.0.php      |    3 -
 .../Model/Resource/Item/Collection.php        |   32 +-
 .../Magento/backend/web/css/admin.less        |    8 +-
 .../Magento/backend/web/css/source/table.less |    3 +-
 .../Magento/backend/web/mui/form.css          |    6 +-
 dev/shell/install.php                         |    4 +
 dev/tests/functional/etc/global/events.xml    |   27 +
 dev/tests/functional/etc/global/events.xsd    |   96 +
 .../Selenium/Element/ConditionsElement.php    |  393 ++
 .../Element/MultiselectgrouplistElement.php   |  312 ++
 .../Util/Generate/Fixture/FieldsProvider.php  |   31 +
 .../lib/Mtf/Util/Generate/testcase.xml        |  140 +-
 dev/tests/functional/phpunit.xml.dist         |    3 +
 .../Backend/Test/Block/FormPageActions.php    |   10 +
 .../Backend/Test/Block/Widget/FormTabs.php    |   15 +-
 .../Backend/Test/Block/Widget/Grid.php        |   15 +-
 .../Backend/Test/Handler/Conditions.php       |  281 ++
 .../Backend/Test/Handler/Pagination.php       |   85 -
 .../Product/{Form.xml => ProductForm.xml}     |    0
 .../Test/Fixture/CatalogProductBundle.php     |    5 +
 .../Edit/{Form.php => CategoryForm.php}       |    5 +-
 .../Edit/{Form.xml => CategoryForm.xml}       |   16 +
 .../Product/Attribute/Edit/AttributeForm.php} |   15 +-
 .../Product/Attribute/Edit/AttributeForm.xml  |  127 +
 .../Product/Attribute/Edit/Tab/Advanced.php   |   65 +
 .../Product/Attribute/Edit/Tab/Options.php    |   61 +
 .../Attribute/Edit/Tab/Options/Option.php     |   46 +
 .../Attribute/Edit/Tab/Options/Option.xml     |   39 +
 .../Adminhtml/Product/Attribute/Grid.php      |   57 +
 .../Product/{Form.php => ProductForm.php}     |   46 +-
 .../Product/{Form.xml => ProductForm.xml}     |    1 +
 .../Catalog/Test/Block/Category/View.php      |   51 +
 .../Test/Block/Product/ListProduct.php        |   31 +-
 .../Block/Product/ProductList/Crosssell.php   |   17 +-
 .../Block/Product/ProductList/Toolbar.php     |   28 +
 .../Catalog/Test/Block/Product/View.php       |   19 +
 .../app/Magento/Catalog/Test/Block/Search.php |   26 +-
 .../AssertAbsenceDeleteAttributeButton.php    |   66 +
 .../AssertAttributeOnAttributeForm.php        |   56 +
 .../AssertAttributeOptionsOnProductForm.php   |   56 +
 .../AssertAttributeSearchableByLabel.php      |   56 +
 .../Test/Constraint/AssertCategoryForm.php    |   56 +
 .../Test/Constraint/AssertCategoryPage.php    |  150 +
 .../Constraint/AssertCategorySaveMessage.php  |   75 +
 .../AssertCrossSellsProductsSection.php       |   87 +
 .../AssertNoCrossSellsProductsSection.php     |   87 +
 .../AssertNoRelatedProductsSection.php        |   82 +
 .../AssertNoUpSellsProductsSection.php        |   82 +
 ...rtProductAttributeDisplayingOnFrontend.php |   56 +
 ...ProductAttributeDisplayingOnSearchForm.php |   56 +
 .../AssertProductAttributeInGrid.php          |   56 +
 .../AssertProductAttributeIsComparable.php    |   56 +
 .../AssertProductAttributeIsFilterable.php    |   56 +
 ...rtProductAttributeIsFilterableInSearch.php |   56 +
 .../AssertProductAttributeIsGlobal.php        |   56 +
 .../AssertProductAttributeIsHtmlAllowed.php   |   56 +
 .../AssertProductAttributeIsRequired.php      |   56 +
 .../AssertProductAttributeIsUnique.php        |   56 +
 ...AssertProductAttributeIsUsedPromoRules.php |   56 +
 .../AssertProductAttributeOnProductForm.php   |   56 +
 .../AssertProductAttributeSaveMessage.php     |   70 +
 ...sertProductAttributeUsedSortOnFrontend.php |   56 +
 .../Test/Constraint/AssertProductForm.php     |    6 +-
 .../Constraint/AssertProductInCategory.php    |    6 +-
 ...AssertProductIsNotDisplayingOnFrontend.php |    6 +-
 .../AssertProductVisibleInCategory.php        |    6 +-
 .../AssertRelatedProductsSection.php          |   82 +
 .../AssertUpSellsProductsSection.php          |   82 +
 ...CategoryEntity.php => CatalogCategory.php} |   90 +-
 ...CategoryEntity.xml => CatalogCategory.xml} |   50 +-
 .../Test/Fixture/CatalogProductAttribute.php  |  559 +++
 .../Test/Fixture/CatalogProductAttribute.xml  |  293 ++
 .../CatalogProductAttribute/Options.php       |  101 +
 .../Test/Fixture/CatalogProductSimple.php     |   17 +
 .../Test/Fixture/CatalogProductSimple.xml     |    6 +
 .../CatalogProductSimple/CategoryIds.php      |   11 +-
 .../Fixture/CatalogProductSimple/Price.php    |    9 +-
 .../Fixture/CatalogProductSimple/TaxClass.php |  116 +
 .../Test/Fixture/CatalogProductVirtual.php    |    6 +
 .../Test/Fixture/CatalogProductVirtual.xml    |    1 +
 .../CatalogCategoryInterface.php}             |    6 +-
 .../Curl.php                                  |    4 +-
 .../Handler/CatalogProductSimple/Curl.php     |  103 +-
 .../Page/Adminhtml/CatalogCategoryEdit.php    |   81 +
 .../Page/Adminhtml/CatalogCategoryEdit.xml    |   45 +
 .../CatalogProductAttributeIndex.php          |   80 +
 .../CatalogProductAttributeIndex.xml          |   45 +
 .../Adminhtml/CatalogProductAttributeNew.php  |   66 +
 .../Adminhtml/CatalogProductAttributeNew.xml  |   39 +
 .../Page/Adminhtml/CatalogProductEdit.php     |    4 +-
 .../Page/Adminhtml/CatalogProductEdit.xml     |    2 +-
 .../Test/Page/Adminhtml/CatalogProductNew.php |    6 +-
 .../Test/Page/Adminhtml/CatalogProductNew.xml |    2 +-
 .../Test/Page/Category/CatalogCategory.php    |    5 +-
 .../Page/Category/CatalogCategoryEdit.php     |    5 +-
 .../Page/Category/CatalogCategoryView.php     |   30 +-
 .../Page/Category/CatalogCategoryView.xml     |   12 +
 ...CategoryEntity.php => CatalogCategory.php} |    4 +-
 .../Test/Repository/CatalogProductSimple.php  |  121 +-
 .../Category/UpdateCategoryEntityTest.php     |  102 +
 .../testUpdateCategory.csv                    |    4 +
 .../CreateVirtualProductEntityTest.php        |   12 +-
 .../testCreate.csv                            |    2 +-
 .../Product/UpdateSimpleProductEntityTest.php |   10 +-
 .../CreateProductAttributeEntityTest.php      |   67 +
 .../testCreateProductAttribute.csv            |    9 +
 .../DeleteSystemProductAttributeTest.php      |   63 +
 .../testDeleteSystemProductAttribute.csv      |    2 +
 .../app/Magento/Catalog/Test/etc/curl/di.xml  |    2 +-
 .../Catalog/Test/etc/global/constraint.xml    |  117 +-
 .../Catalog/Test/etc/global/fixture.xml       |   12 +-
 .../Magento/Catalog/Test/etc/global/page.xml  |   15 +
 .../{Form/Advanced.php => Advanced/Form.php}  |   60 +-
 .../Test/Block/Advanced/Form.xml              |   51 +
 .../Test/Block/Advanced/Result.php            |  127 +
 .../AssertAdvancedSearchProductsResult.php    |  185 +
 .../AssertSuggestSearchingResult.php          |    6 +-
 .../Test/Page/AdvancedResult.php              |   71 +
 .../Test/Page/AdvancedResult.xml              |   39 +
 .../Test/Page/AdvancedSearch.php              |   52 +
 .../Test/Page/AdvancedSearch.xml              |   33 +
 .../Test/Page/CatalogsearchResult.php         |   39 +-
 .../Test/Page/CatalogsearchResult.xml         |   33 +
 .../TestCase/AdvancedSearchEntityTest.php     |  103 +
 .../AdvancedSearchEntityTest/testSearch.csv   |   14 +
 .../Test/TestCase/AdvancedSearchTest.php      |    2 +-
 .../Test/etc/global/constraint.xml            |    7 +
 .../CatalogSearch/Test/etc/global/page.xml    |   40 +
 .../Test/Block/Cart/DiscountCodes.php         |   79 +
 .../Checkout/Test/Block/Cart/Shipping.php     |  149 +
 .../Checkout/Test/Block/Cart/Shipping.xml     |   39 +
 .../Checkout/Test/Block/Cart/Totals.php       |  147 +
 .../Checkout/Test/Page/CheckoutCart.php       |  124 +-
 .../Checkout/Test/Page/CheckoutCart.xml       |   63 +
 .../app/Magento/Cms/Test/Page/CmsIndex.php    |    2 -
 .../Product/Edit/Tab/Super/Config.php         |    6 +-
 .../Block/Adminhtml/Product/ProductForm.php   |  227 +-
 .../Block/Adminhtml/Product/ProductForm.xml   |   68 -
 .../AssertConfigurableInCategory.php          |   10 +-
 .../Constraint/AssertConfigurableInGrid.php   |    8 +-
 .../AssertProductAttributeIsConfigurable.php  |  106 +
 .../Fixture/CatalogProductConfigurable.php    |   48 +-
 .../Page/Adminhtml/CatalogProductNew.php}     |   43 +-
 .../Test/Page/Adminhtml/CatalogProductNew.xml |   33 +
 .../Repository/CatalogProductConfigurable.php |   44 +
 .../Product/CreateConfigurableEntityTest.php  |   16 +-
 .../Test/etc/global/constraint.xml            |    8 +
 .../Edit/{Form.php => CustomerForm.php}       |    5 +-
 .../Edit/{Form.xml => CustomerForm.xml}       |    0
 .../AssertCustomerFailRegisterMessage.php     |   66 +
 .../Test/Fixture/AddressInjectable.php        |    1 -
 .../Test/Page/Adminhtml/CustomerIndexEdit.php |    4 +-
 .../Test/Page/Adminhtml/CustomerIndexEdit.xml |    2 +-
 .../Test/Page/Adminhtml/CustomerIndexNew.php  |    4 +-
 .../Test/Page/Adminhtml/CustomerIndexNew.xml  |    2 +-
 .../Test/Page/CustomerAccountCreate.php       |    1 -
 .../CreateExistingCustomerFrontendEntity.php  |  120 +
 .../testCreateExistingCustomer.csv            |    2 +
 .../app/Magento/Customer/Test/etc/curl/di.xml |    6 +-
 .../Customer/Test/etc/global/constraint.xml   |    6 +
 .../Product/{Form.xml => ProductForm.xml}     |    0
 .../AssertDownloadableProductForm.php         |   12 +-
 .../Fixture/CatalogProductDownloadable.php    |    9 +-
 .../CreateDownloadableProductEntityTest.php   |   16 +-
 .../testCreateDownloadableProduct.csv         |    2 +-
 .../Adminhtml/Rating/Edit/RatingForm.php      |   36 +
 .../Adminhtml/Rating/Edit/RatingForm.xml      |   41 +
 .../Test/Block/Adminhtml/Rating/Grid.php      |   56 +
 .../app/Magento/Review/Test/Block/Form.php    |   32 +-
 .../Constraint/AssertProductRatingInGrid.php  |   56 +
 .../AssertProductRatingInProductPage.php      |   77 +
 .../AssertProductRatingNotInProductPage.php   |   77 +
 .../AssertProductRatingSuccessSaveMessage.php |   71 +
 .../Magento/Review/Test/Fixture/Rating.php    |  128 +
 .../Magento/Review/Test/Fixture/Rating.xml    |   79 +
 .../Review/Test/Page/Adminhtml/RatingEdit.php |   68 +
 .../Review/Test/Page/Adminhtml/RatingEdit.xml |   39 +
 .../Test/Page/Adminhtml/RatingIndex.php       |   80 +
 .../Test/Page/Adminhtml/RatingIndex.xml       |   45 +
 .../Review/Test/Page/Adminhtml/RatingNew.php  |   66 +
 .../Review/Test/Page/Adminhtml/RatingNew.xml  |   39 +
 .../CreateBackendProductRatingTest.php        |  129 +
 .../testCreateBackendProductRating.csv        |    3 +
 .../Review/Test/etc/global/constraint.xml     |   39 +
 .../Review/Test/etc/global/fixture.xml        |    8 +
 .../Magento/Review/Test/etc/global/page.xml   |   42 +
 .../Test/Block/Adminhtml/Rate/Edit/Form.php   |    4 +-
 .../Adminhtml/Rate/Edit/FormPageActions.php   |    4 +-
 .../Block/Adminhtml/Rate/GridPageActions.php  |   41 +
 .../Tax/Test/Block/Adminhtml/Rule/Grid.php    |    3 +-
 .../Tax/Test/Constraint/AssertTaxRateForm.php |   11 +-
 .../Constraint/AssertTaxRateInTaxRule.php     |   56 +
 .../Test/Constraint/AssertTaxRuleApplying.php |  165 +
 .../Constraint/AssertTaxRuleIsApplied.php     |   66 +-
 .../Constraint/AssertTaxRuleIsNotApplied.php  |   69 +-
 .../Constraint/AssertTaxRuleNotInGrid.php     |   74 +
 .../AssertTaxRuleSuccessDeleteMessage.php     |   71 +
 .../Tax/Test/Page/Adminhtml/TaxRateIndex.php  |    4 +-
 .../Tax/Test/Page/Adminhtml/TaxRateIndex.xml  |    2 +-
 .../Magento/Tax/Test/Repository/TaxClass.php  |   10 +
 .../Magento/Tax/Test/Repository/TaxRule.php   |    4 +-
 .../Test/TestCase/CreateTaxRateEntityTest.php |   92 +
 .../testCreateTaxRate.csv                     |    6 +
 .../Test/TestCase/DeleteTaxRuleEntityTest.php |  118 +
 .../testDeleteTaxRule.csv                     |    2 +
 .../Test/TestCase/UpdateTaxRuleEntityTest.php |    7 +-
 .../testUpdateTaxRule.csv                     |   10 +-
 .../app/Magento/Tax/Test/etc/curl/di.xml      |    2 +-
 .../Tax/Test/etc/global/constraint.xml        |   17 +
 .../AssertProductUrlAvailableOnTheFront.php   |   77 +
 .../AssertUrlRewriteCategoryRedirect.php      |   16 +-
 .../UrlRewrite/Test/Fixture/UrlRewrite.php    |   11 +
 .../UrlRewrite/Test/Fixture/UrlRewrite.xml    |    9 +-
 .../Test/Fixture/UrlRewrite/ProductId.php     |  109 +
 .../Test/Handler/UrlRewrite/Curl.php          |    2 +-
 .../UrlRewrite/Test/Repository/UrlRewrite.php |    2 +-
 ...hp => CreateCategoryRewriteEntityTest.php} |   10 +-
 .../testCreateCategoryRewrite.csv}            |    0
 ... => DeleteProductUrlRewriteEntityTest.php} |    4 +-
 .../testDeleteProductUrlRewrite.csv}          |    0
 .../UpdateCategoryUrlRewriteEntityTest.php    |  116 +
 .../testUpdateCategoryUrlRewrite.csv          |    5 +
 .../UpdateProductUrlRewriteEntityTest.php     |  111 +
 .../testUpdateProductUrlRewrite.csv           |    3 +
 .../Magento/UrlRewrite/Test/etc/curl/di.xml   |    2 +-
 .../UrlRewrite/Test/etc/global/constraint.xml |    9 +
 .../Adminhtml/Role/{Edit.php => RoleForm.php} |    4 +-
 .../Adminhtml/Role/{Edit.xml => RoleForm.xml} |    0
 .../Test/Page/Adminhtml/UserRoleEditRole.php  |    4 +-
 .../Test/Page/Adminhtml/UserRoleEditRole.xml  |    2 +-
 .../app/Magento/User/Test/etc/curl/di.xml     |    2 +-
 .../Magento/TestFramework/Bootstrap.php       |   27 +-
 dev/tests/integration/phpunit.xml.dist        |    2 +
 .../Magento/Catalog/Model/CategoryTest.php    |    5 +
 .../Model/Config/Backend/ManagestockTest.php  |   89 +
 .../CatalogInventory/Model/Stock/ItemTest.php |   64 +-
 .../testsuite/Magento/DatabaseTest.php        |   51 +
 .../Model/Validator/Attribute/BackendTest.php |    4 +-
 .../Adminhtml/Order/CreditmemoTest.php        |   20 +-
 .../Magento/Sales/_files/order_info.php       |    7 +-
 .../Integrity/Modular/LayoutFilesTest.php     |    1 +
 dev/tests/js/jsTestDriver.php.dist            |    2 +-
 .../Magento/Test/Legacy/ObsoleteCodeTest.php  |    1 -
 .../Test/Legacy/_files/obsolete_methods.php   |    7 +
 .../Legacy/_files/obsolete_properties.php     |    2 +
 .../Php/_files/phpcpd/blacklist/common.txt    |    1 +
 .../Block/ToolbarEntryTest.php                |   27 +
 .../Product/Link/Product/CollectionTest.php   |  164 +
 .../Catalog/Service/V1/Data/ConverterTest.php |  112 +
 .../Data/Eav/AttributeMetadataBuilderTest.php |  154 +
 .../V1/Data/Eav/AttributeMetadataTest.php     |  131 +
 .../Service/V1/Data/Eav/OptionTest.php        |   44 +
 .../Service/V1/Data/ProductBuilderTest.php    |  126 +
 .../Service/V1/Data/ProductMapperTest.php     |   71 +
 .../V1/Product/Link/ReadServiceTest.php       |    2 +-
 .../V1/Product/Link/WriteServiceTest.php      |    2 +-
 .../Product/{Link => }/ProductLoaderTest.php  |    2 +-
 .../V1/ProductAttributeReadServiceTest.php    |   90 +
 .../Service/V1/ProductMetadataServiceTest.php |   89 +
 .../Catalog/Service/V1/ProductServiceTest.php |  403 ++
 .../Block/QtyincrementsTest.php               |   70 +-
 .../Block/Stockqty/DefaultStockqtyTest.php    |   96 +-
 .../CatalogInventory/Model/Stock/ItemTest.php |  574 ++-
 .../Service/V1/StockItemTest.php              |  462 ++
 .../Service/V1/StockStatusServiceTest.php     |   70 +
 .../Magento/CatalogSearch/Helper/DataTest.php |  173 +
 .../Magento/Checkout/Model/CartTest.php       |  128 +
 .../ConfigurableProduct/Helper/DataTest.php   |  200 +
 .../Model/Export/RowCustomizerTest.php        |  236 +
 .../Model/Product/Type/ConfigurableTest.php   |   45 +
 .../Model/Product/Type/PluginTest.php         |   89 +
 .../Option/Plugin/ConfigurableProductTest.php |   95 +
 .../Framework/DB/Adapter/Pdo/MysqlTest.php    |   84 -
 .../DB/Helper/AbstractHelperTest.php          |  174 +
 .../Magento/Framework/DB/Tree/NodeTest.php    |  135 +
 .../Argument/Interpreter/ArrayTypeTest.php    |   66 +-
 .../Argument/_files/typesInvalidArray.php     |    5 -
 .../Data/Argument/_files/types_valid.xml      |    1 +
 .../Install/Model/Installer/ConsoleTest.php   |  182 +-
 .../Magento/Sales/Model/OrderTest.php         |   12 +-
 lib/internal/Magento/Framework/App/Config.php |    2 +-
 .../Framework/App/EntryPoint/EntryPoint.php   |    4 +-
 .../Magento/Framework/AppInterface.php        |    2 +-
 .../Framework/DB/Adapter/Pdo/Mysql.php        |    2 +-
 .../Framework/DB/Helper/AbstractHelper.php    |  130 -
 .../Data/Argument/Interpreter/ArrayType.php   |    4 +-
 .../Framework/Data/etc/argument/types.xsd     |    2 +-
 .../jquery-ui-timepicker-addon-1.0.1.js       | 1530 -------
 lib/web/mage/backend/floating-header.js       |    9 +-
 pub/index.php                                 |    2 -
 413 files changed, 19087 insertions(+), 8256 deletions(-)
 create mode 100644 app/code/Magento/Bundle/Model/Plugin/PriceBackend.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/Converter.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadata.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataBuilder.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/Eav/Option.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/Eav/OptionBuilder.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/Eav/ValidationRule.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/Eav/ValidationRuleBuilder.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/Product.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/ProductAttributeType.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/ProductAttributeTypeBuilder.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/ProductBuilder.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/ProductMapper.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/SearchResults.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/Data/SearchResultsBuilder.php
 rename app/code/Magento/Catalog/Service/V1/Product/{Link => }/ProductLoader.php (86%)
 create mode 100644 app/code/Magento/Catalog/Service/V1/ProductAttributeReadService.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/ProductAttributeReadServiceInterface.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/ProductMetadataService.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/ProductMetadataServiceInterface.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/ProductService.php
 create mode 100644 app/code/Magento/Catalog/Service/V1/ProductServiceInterface.php
 delete mode 100644 app/code/Magento/Catalog/sql/catalog_setup/install-1.6.0.0.php
 create mode 100644 app/code/Magento/CatalogInventory/Model/Stock/ItemRegistry.php
 create mode 100644 app/code/Magento/CatalogInventory/Service/V1/Data/StockItem.php
 create mode 100644 app/code/Magento/CatalogInventory/Service/V1/Data/StockItemBuilder.php
 create mode 100644 app/code/Magento/CatalogInventory/Service/V1/StockItem.php
 create mode 100644 app/code/Magento/CatalogInventory/Service/V1/StockItemInterface.php
 create mode 100644 app/code/Magento/CatalogInventory/Service/V1/StockStatusService.php
 create mode 100644 app/code/Magento/CatalogInventory/Service/V1/StockStatusServiceInterface.php
 create mode 100644 dev/tests/functional/etc/global/events.xml
 create mode 100644 dev/tests/functional/etc/global/events.xsd
 create mode 100644 dev/tests/functional/lib/Mtf/Client/Driver/Selenium/Element/ConditionsElement.php
 create mode 100644 dev/tests/functional/lib/Mtf/Client/Driver/Selenium/Element/MultiselectgrouplistElement.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Backend/Test/Handler/Conditions.php
 delete mode 100644 dev/tests/functional/tests/app/Magento/Backend/Test/Handler/Pagination.php
 rename dev/tests/functional/tests/app/Magento/Bundle/Test/Block/Adminhtml/Product/{Form.xml => ProductForm.xml} (100%)
 rename dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/{Form.php => CategoryForm.php} (96%)
 rename dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/{Form.xml => CategoryForm.xml} (76%)
 rename dev/tests/functional/tests/app/Magento/{CatalogSearch/Test/Page/Advanced/Result.php => Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/AttributeForm.php} (76%)
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/AttributeForm.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Advanced.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options/Option.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options/Option.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Grid.php
 rename dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/{Form.php => ProductForm.php} (92%)
 rename dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/{Form.xml => ProductForm.xml} (99%)
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Category/View.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAbsenceDeleteAttributeButton.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeOnAttributeForm.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeOptionsOnProductForm.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeSearchableByLabel.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategoryForm.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategoryPage.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategorySaveMessage.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCrossSellsProductsSection.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoCrossSellsProductsSection.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoRelatedProductsSection.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoUpSellsProductsSection.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeDisplayingOnFrontend.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeDisplayingOnSearchForm.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeInGrid.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsComparable.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsFilterable.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsFilterableInSearch.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsGlobal.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsHtmlAllowed.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsRequired.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsUnique.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsUsedPromoRules.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeOnProductForm.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeSaveMessage.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeUsedSortOnFrontend.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertRelatedProductsSection.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertUpSellsProductsSection.php
 rename dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/{CatalogCategoryEntity.php => CatalogCategory.php} (70%)
 rename dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/{CatalogCategoryEntity.xml => CatalogCategory.xml} (70%)
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute/Options.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/TaxClass.php
 rename dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/{CatalogCategoryEntity/CatalogCategoryEntityInterface.php => CatalogCategory/CatalogCategoryInterface.php} (84%)
 rename dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/{CatalogCategoryEntity => CatalogCategory}/Curl.php (95%)
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogCategoryEdit.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogCategoryEdit.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeIndex.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeIndex.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeNew.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeNew.xml
 rename dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/{CatalogCategoryEntity.php => CatalogCategory.php} (94%)
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Category/UpdateCategoryEntityTest.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Category/UpdateCategoryEntityTest/testUpdateCategory.csv
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/CreateProductAttributeEntityTest.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/CreateProductAttributeEntityTest/testCreateProductAttribute.csv
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/DeleteSystemProductAttributeTest.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/DeleteSystemProductAttributeTest/testDeleteSystemProductAttribute.csv
 rename dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/{Form/Advanced.php => Advanced/Form.php} (64%)
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Form.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Result.php
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Constraint/AssertAdvancedSearchProductsResult.php
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedResult.php
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedResult.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedSearch.php
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedSearch.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/CatalogsearchResult.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchEntityTest.php
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchEntityTest/testSearch.csv
 create mode 100644 dev/tests/functional/tests/app/Magento/CatalogSearch/Test/etc/global/page.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/DiscountCodes.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Shipping.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Shipping.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Totals.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Checkout/Test/Page/CheckoutCart.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertProductAttributeIsConfigurable.php
 rename dev/tests/functional/tests/app/Magento/{CatalogSearch/Test/Page/Advanced.php => ConfigurableProduct/Test/Page/Adminhtml/CatalogProductNew.php} (56%)
 create mode 100644 dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Page/Adminhtml/CatalogProductNew.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Repository/CatalogProductConfigurable.php
 rename dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/{Form.php => CustomerForm.php} (98%)
 rename dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/{Form.xml => CustomerForm.xml} (100%)
 create mode 100644 dev/tests/functional/tests/app/Magento/Customer/Test/Constraint/AssertCustomerFailRegisterMessage.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Customer/Test/TestCase/CreateExistingCustomerFrontendEntity.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Customer/Test/TestCase/CreateExistingCustomerFrontendEntity/testCreateExistingCustomer.csv
 rename dev/tests/functional/tests/app/Magento/Downloadable/Test/Block/Adminhtml/Product/{Form.xml => ProductForm.xml} (100%)
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Edit/RatingForm.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Edit/RatingForm.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Grid.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingInGrid.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingInProductPage.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingNotInProductPage.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingSuccessSaveMessage.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Fixture/Rating.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Fixture/Rating.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingEdit.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingEdit.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingIndex.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingIndex.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingNew.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingNew.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/TestCase/CreateBackendProductRatingTest.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/TestCase/CreateBackendProductRatingTest/testCreateBackendProductRating.csv
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/etc/global/constraint.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Review/Test/etc/global/page.xml
 create mode 100644 dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/GridPageActions.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRateInTaxRule.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleApplying.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleNotInGrid.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleSuccessDeleteMessage.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/CreateTaxRateEntityTest.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/CreateTaxRateEntityTest/testCreateTaxRate.csv
 create mode 100644 dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/DeleteTaxRuleEntityTest.php
 create mode 100644 dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/DeleteTaxRuleEntityTest/testDeleteTaxRule.csv
 create mode 100644 dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Constraint/AssertProductUrlAvailableOnTheFront.php
 create mode 100644 dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite/ProductId.php
 rename dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/{CreateCategoryRewritesEntityTest.php => CreateCategoryRewriteEntityTest.php} (90%)
 rename dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/{CreateCategoryRewritesEntityTest/testCreateCategoryRewrites.csv => CreateCategoryRewriteEntityTest/testCreateCategoryRewrite.csv} (100%)
 rename dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/{DeleteProductUrlRewritesEntityTest.php => DeleteProductUrlRewriteEntityTest.php} (96%)
 rename dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/{DeleteProductUrlRewritesEntityTest/testDeleteProductUrlRewrites.csv => DeleteProductUrlRewriteEntityTest/testDeleteProductUrlRewrite.csv} (100%)
 create mode 100644 dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateCategoryUrlRewriteEntityTest.php
 create mode 100644 dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateCategoryUrlRewriteEntityTest/testUpdateCategoryUrlRewrite.csv
 create mode 100644 dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateProductUrlRewriteEntityTest.php
 create mode 100644 dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateProductUrlRewriteEntityTest/testUpdateProductUrlRewrite.csv
 rename dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/{Edit.php => RoleForm.php} (95%)
 rename dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/{Edit.xml => RoleForm.xml} (100%)
 create mode 100644 dev/tests/integration/testsuite/Magento/CatalogInventory/Model/Config/Backend/ManagestockTest.php
 create mode 100644 dev/tests/integration/testsuite/Magento/DatabaseTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Catalog/Model/Resource/Product/Link/Product/CollectionTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ConverterTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataBuilderTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/OptionTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ProductBuilderTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ProductMapperTest.php
 rename dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/{Link => }/ProductLoaderTest.php (98%)
 create mode 100644 dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductAttributeReadServiceTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductMetadataServiceTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductServiceTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/CatalogInventory/Service/V1/StockItemTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/CatalogInventory/Service/V1/StockStatusServiceTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/CatalogSearch/Helper/DataTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Checkout/Model/CartTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/ConfigurableProduct/Helper/DataTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Export/RowCustomizerTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Product/Type/PluginTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Quote/Item/QuantityValidator/Initializer/Option/Plugin/ConfigurableProductTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Framework/DB/Helper/AbstractHelperTest.php
 create mode 100644 dev/tests/unit/testsuite/Magento/Framework/DB/Tree/NodeTest.php
 delete mode 100644 lib/web/jquery/jquery-ui-timepicker-addon-1.0.1.js

diff --git a/CHANGELOG.md b/CHANGELOG.md
index f81444dc9b1..23ebdb30c71 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,50 @@
+2.0.0.0-dev82
+=============
+* Added support for MTF Reporting Tool
+* Framework improvements:
+  * Covered the following Magento application components with unit tests:
+      * `ConfigurableProduct/Helper/Data.php`
+      * `ConfigurableProduct/Model/Export/RowCustomizer.php`
+      * `ConfigurableProduct/Model/Product/Type/Configurable.php`
+      * `ConfigurableProduct/Model/Product/Type/Plugin.php`
+      * `ConfigurableProduct/Model/Quote/Item/QuantityValidator/Initializer/Option/Plugin/ConfigurableProduct.php`
+      * `CatalogSearch/Helper/Data.php`
+  * Covered Magento lib with unit tests:
+      * `lib/internal/Magento/Framework/DB/Helper/AbstractHelper.php`
+      * `lib/internal/Magento/Framework/DB/Tree/Node.php`
+* Created Service API for Magento_Catalog Module:
+  * Implemented the Product API
+  * Implemented the ProductAttributeRead API
+* Fixed bugs:
+  * Fixed issues with form elements visibility on the backend
+  * Fixed an issue where backend forms contained an excessive container
+  * Fixed an issue where a wrong category structure was displayed on the Category page
+  * Fixed an issue where the pub/index.php entry point was broken because of the obsolete constants
+  * Fixed an issue where it was impossible to pass an empty array as an argument in DI configuration and layout updates
+  * Fixed an issue with status and visibility settings of a related product on the backend
+  * Fixed an issue with unused DB indexes, which used resources, but did not contribute to higher performance
+  * Fixed an issue where it was possible to create a downloadable product without specifying a link or a file
+  * Fixed an issue where a fatal error occured when opening a fixed bundle product with custom options page on the frontend
+  * Fixed an issue where the was a wrong config key for backend cataloginventory
+* Processed GitHub requests:
+  * [#548] (https://github.com/magento/magento2/issues/548) -- Console installer doesn't checks filesystem permissions
+  * [#552] (https://github.com/magento/magento2/issues/552) -- backend notifications sitebuild bug
+  * [#562] (https://github.com/magento/magento2/pull/562) -- Bugfix Magento\Framework\DB\Adapter\Pdo\Mysql::getCreateTable()
+  * [#565] (https://github.com/magento/magento2/pull/565) -- Magento\CatalogSearch\Model\Query::getResultCollection() not working
+  * [#557] (https://github.com/magento/magento2/issues/557) -- translation anomalies backend login page
+* Added the following functional tests:
+  * Advanced Search
+  * Existing Customer Creation
+  * Product Attribute Creation
+  * Product Rating Creation
+  * Sales Rule Creation
+  * System Product Attribute Deletion
+  * Tax Rate Creation
+  * Tax Rule Deletion
+  * Update Category
+  * Update Category Url Rewrite
+  * Update Product Url Rewrite
+
 2.0.0.0-dev81
 =============
 * Framework improvements:
diff --git a/app/code/Magento/AdminNotification/Block/ToolbarEntry.php b/app/code/Magento/AdminNotification/Block/ToolbarEntry.php
index 24c1ec71d08..fb4f4507a5f 100644
--- a/app/code/Magento/AdminNotification/Block/ToolbarEntry.php
+++ b/app/code/Magento/AdminNotification/Block/ToolbarEntry.php
@@ -30,6 +30,11 @@ namespace Magento\AdminNotification\Block;
  */
 class ToolbarEntry extends \Magento\Backend\Block\Template
 {
+    /**
+     * Number of notifications showed on expandable window
+     */
+    const NOTIFICATIONS_NUMBER = 4;
+
     /**
      * Collection of latest unread notifications
      *
@@ -68,7 +73,7 @@ class ToolbarEntry extends \Magento\Backend\Block\Template
      */
     public function getLatestUnreadNotifications()
     {
-        return $this->_notificationList;
+        return $this->_notificationList->setPageSize(self::NOTIFICATIONS_NUMBER);
     }
 
     /**
diff --git a/app/code/Magento/Backend/Block/Widget/Grid/Extended.php b/app/code/Magento/Backend/Block/Widget/Grid/Extended.php
index 55a821fd923..10431af3952 100644
--- a/app/code/Magento/Backend/Block/Widget/Grid/Extended.php
+++ b/app/code/Magento/Backend/Block/Widget/Grid/Extended.php
@@ -46,7 +46,7 @@ class Extended extends \Magento\Backend\Block\Widget\Grid implements \Magento\Ba
      *
      * @var \Magento\Framework\Data\Collection
      */
-    protected $_collection = null;
+    protected $_collection;
 
     /**
      * Export flag
@@ -81,14 +81,14 @@ class Extended extends \Magento\Backend\Block\Widget\Grid implements \Magento\Ba
      *
      * @var string
      */
-    protected $_massactionIdField = null;
+    protected $_massactionIdField;
 
     /**
      * Massaction row id filter
      *
      * @var string
      */
-    protected $_massactionIdFilter = null;
+    protected $_massactionIdFilter;
 
     /**
      * Massaction block name
@@ -202,9 +202,7 @@ class Extended extends \Magento\Backend\Block\Widget\Grid implements \Magento\Ba
     {
         $this->setChild(
             'export_button',
-            $this->getLayout()->createBlock(
-                'Magento\Backend\Block\Widget\Button'
-            )->setData(
+            $this->getLayout()->createBlock('Magento\Backend\Block\Widget\Button')->setData(
                 array(
                     'label' => __('Export'),
                     'onclick' => $this->getJsObjectName() . '.doExport()',
@@ -214,17 +212,13 @@ class Extended extends \Magento\Backend\Block\Widget\Grid implements \Magento\Ba
         );
         $this->setChild(
             'reset_filter_button',
-            $this->getLayout()->createBlock(
-                'Magento\Backend\Block\Widget\Button'
-            )->setData(
+            $this->getLayout()->createBlock('Magento\Backend\Block\Widget\Button')->setData(
                 array('label' => __('Reset Filter'), 'onclick' => $this->getJsObjectName() . '.resetFilter()')
             )
         );
         $this->setChild(
             'search_button',
-            $this->getLayout()->createBlock(
-                'Magento\Backend\Block\Widget\Button'
-            )->setData(
+            $this->getLayout()->createBlock('Magento\Backend\Block\Widget\Button')->setData(
                 array(
                     'label' => __('Search'),
                     'onclick' => $this->getJsObjectName() . '.doFilter()',
@@ -289,15 +283,11 @@ class Extended extends \Magento\Backend\Block\Widget\Grid implements \Magento\Ba
         if (is_array($column)) {
             $this->getColumnSet()->setChild(
                 $columnId,
-                $this->getLayout()->createBlock(
-                    'Magento\Backend\Block\Widget\Grid\Column\Extended'
-                )->setData(
-                    $column
-                )->setId(
-                    $columnId
-                )->setGrid(
-                    $this
-                )
+                $this->getLayout()
+                    ->createBlock('Magento\Backend\Block\Widget\Grid\Column\Extended')
+                    ->setData($column)
+                    ->setId($columnId)
+                    ->setGrid($this)
             );
             $this->getColumnSet()->getChildBlock($columnId)->setGrid($this);
         } else {
@@ -437,19 +427,19 @@ class Extended extends \Magento\Backend\Block\Widget\Grid implements \Magento\Ba
     protected function _prepareMassactionColumn()
     {
         $columnId = 'massaction';
-        $massactionColumn = $this->getLayout()->createBlock(
-            'Magento\Backend\Block\Widget\Grid\Column'
-        )->setData(
-            array(
-                'index' => $this->getMassactionIdField(),
-                'filter_index' => $this->getMassactionIdFilter(),
-                'type' => 'massaction',
-                'name' => $this->getMassactionBlock()->getFormFieldName(),
-                'is_system' => true,
-                'header_css_class' => 'col-select',
-                'column_css_class' => 'col-select'
-            )
-        );
+        $massactionColumn = $this->getLayout()
+            ->createBlock('Magento\Backend\Block\Widget\Grid\Column')
+            ->setData(
+                array(
+                    'index' => $this->getMassactionIdField(),
+                    'filter_index' => $this->getMassactionIdFilter(),
+                    'type' => 'massaction',
+                    'name' => $this->getMassactionBlock()->getFormFieldName(),
+                    'is_system' => true,
+                    'header_css_class' => 'col-select',
+                    'column_css_class' => 'col-select'
+                )
+            );
 
         if ($this->getNoFilterMassactionColumn()) {
             $massactionColumn->setData('filter', false);
@@ -980,8 +970,10 @@ class Extended extends \Magento\Backend\Block\Widget\Grid implements \Magento\Ba
      * @param \Magento\Framework\Filesystem\File\WriteInterface $stream
      * @return void
      */
-    protected function _exportCsvItem(\Magento\Framework\Object $item, \Magento\Framework\Filesystem\File\WriteInterface $stream)
-    {
+    protected function _exportCsvItem(
+        \Magento\Framework\Object $item,
+        \Magento\Framework\Filesystem\File\WriteInterface $stream
+    ) {
         $row = array();
         foreach ($this->getColumns() as $column) {
             if (!$column->getIsSystem()) {
@@ -1142,7 +1134,10 @@ class Extended extends \Magento\Backend\Block\Widget\Grid implements \Magento\Ba
         $this->_isExport = true;
         $this->_prepareGrid();
 
-        $convert = new \Magento\Framework\Convert\Excel($this->getCollection()->getIterator(), array($this, 'getRowRecord'));
+        $convert = new \Magento\Framework\Convert\Excel(
+            $this->getCollection()->getIterator(),
+            array($this, 'getRowRecord')
+        );
 
         $name = md5(microtime());
         $file = $this->_path . '/' . $name . '.xml';
diff --git a/app/code/Magento/Backend/view/adminhtml/layout/default.xml b/app/code/Magento/Backend/view/adminhtml/layout/default.xml
index 176052180d4..28158275162 100644
--- a/app/code/Magento/Backend/view/adminhtml/layout/default.xml
+++ b/app/code/Magento/Backend/view/adminhtml/layout/default.xml
@@ -203,7 +203,7 @@
             </block>
             <block class="Magento\Theme\Block\Html\Head\Script" name="jquery-jquery-ui-timepicker-addon-js">
                 <arguments>
-                    <argument name="file" xsi:type="string">jquery/jquery-ui-timepicker-addon-1.0.1.js</argument>
+                    <argument name="file" xsi:type="string">jquery/jquery-ui-timepicker-addon.js</argument>
                 </arguments>
             </block>
             <block class="Magento\Theme\Block\Html\Head\Script" name="magento-calendar-js">
diff --git a/app/code/Magento/Backend/view/adminhtml/templates/admin/login.phtml b/app/code/Magento/Backend/view/adminhtml/templates/admin/login.phtml
index 1e8397536ac..feac8432817 100644
--- a/app/code/Magento/Backend/view/adminhtml/templates/admin/login.phtml
+++ b/app/code/Magento/Backend/view/adminhtml/templates/admin/login.phtml
@@ -72,7 +72,7 @@
                         <div class="field field-username">
                             <label for="username" class="label"><span><?php echo __('User Name:') ?></span></label>
                             <div class="control">
-                                <input type="text" id="username" name="login[username]" value="" class="required-entry input-text" placeholder="user name" />
+                                <input type="text" id="username" name="login[username]" value="" class="required-entry input-text" placeholder="<?php echo __('user name') ?>" />
                             </div>
                         </div>
                         <div class="field field-password">
@@ -80,7 +80,7 @@
                             <div class="control">
                                 <!-- This is a dummy hidden field to trick firefox from auto filling the password -->
                                 <input type="text" class="input-text no-display" name="dummy" id="dummy" />
-                                <input type="password" id="login" name="login[password]" class="required-entry input-text" value="" placeholder="password" />
+                                <input type="password" id="login" name="login[password]" class="required-entry input-text" value="" placeholder="<?php echo __('password') ?>" />
                             </div>
                         </div>
                         <?php echo $this->getChildHtml('form.additional.info'); ?>
diff --git a/app/code/Magento/Bundle/Model/Plugin/PriceBackend.php b/app/code/Magento/Bundle/Model/Plugin/PriceBackend.php
new file mode 100644
index 00000000000..61dd8091c80
--- /dev/null
+++ b/app/code/Magento/Bundle/Model/Plugin/PriceBackend.php
@@ -0,0 +1,51 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Bundle\Model\Plugin;
+
+/**
+ * Class PriceBackend
+ *
+ *  Make price validation optional for bundle dynamic
+ */
+class PriceBackend
+{
+    /**
+     * @param \Magento\Catalog\Model\Product\Attribute\Backend\Price $subject
+     * @param Closure $proceed
+     * @param \Magento\Catalog\Model\Product $product
+     * @return bool
+     * @SuppressWarnings(PHPMD.UnusedFormalParameter)
+     */
+    public function aroundValidate(
+        \Magento\Catalog\Model\Product\Attribute\Backend\Price $subject,
+        \Closure $proceed,
+        \Magento\Catalog\Model\Product $product
+    ) {
+        if ($product->getPriceType() == \Magento\Bundle\Model\Product\Price::PRICE_TYPE_DYNAMIC) {
+            return true;
+        } else {
+            return $proceed($product);
+        }
+    }
+}
diff --git a/app/code/Magento/Bundle/etc/adminhtml/di.xml b/app/code/Magento/Bundle/etc/adminhtml/di.xml
index 59d4ad89ff9..aa8319a0538 100644
--- a/app/code/Magento/Bundle/etc/adminhtml/di.xml
+++ b/app/code/Magento/Bundle/etc/adminhtml/di.xml
@@ -37,4 +37,7 @@
             </argument>
         </arguments>
     </type>
+    <type name="Magento\Catalog\Model\Product\Attribute\Backend\Price">
+        <plugin name="bundle" type="Magento\Bundle\Model\Plugin\PriceBackend" sortOrder="100" />
+    </type>
 </config>
diff --git a/app/code/Magento/Bundle/etc/di.xml b/app/code/Magento/Bundle/etc/di.xml
index 9db37f542c8..375f3cd2271 100644
--- a/app/code/Magento/Bundle/etc/di.xml
+++ b/app/code/Magento/Bundle/etc/di.xml
@@ -71,6 +71,7 @@
                 <item name="group_price" xsi:type="string">Magento\Bundle\Pricing\Price\GroupPrice</item>
                 <item name="special_price" xsi:type="string">Magento\Bundle\Pricing\Price\SpecialPrice</item>
                 <item name="msrp_price" xsi:type="string">Magento\Catalog\Pricing\Price\MsrpPrice</item>
+                <item name="custom_option_price" xsi:type="string">Magento\Catalog\Pricing\Price\CustomOptionPrice</item>
                 <item name="base_price" xsi:type="string">Magento\Catalog\Pricing\Price\BasePrice</item>
                 <item name="configured_price" xsi:type="string">Magento\Bundle\Pricing\Price\ConfiguredPrice</item>
                 <item name="bundle_option" xsi:type="string">Magento\Bundle\Pricing\Price\BundleOptionPrice</item>
diff --git a/app/code/Magento/Catalog/Block/Adminhtml/Product/Edit/Action/Attribute/Tab/Inventory.php b/app/code/Magento/Catalog/Block/Adminhtml/Product/Edit/Action/Attribute/Tab/Inventory.php
index f805cecb487..42e110173f3 100644
--- a/app/code/Magento/Catalog/Block/Adminhtml/Product/Edit/Action/Attribute/Tab/Inventory.php
+++ b/app/code/Magento/Catalog/Block/Adminhtml/Product/Edit/Action/Attribute/Tab/Inventory.php
@@ -22,15 +22,13 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-/**
- * Products mass update inventory tab
- *
- * @author      Magento Core Team <core@magentocommerce.com>
- */
 namespace Magento\Catalog\Block\Adminhtml\Product\Edit\Action\Attribute\Tab;
 
 use Magento\CatalogInventory\Model\Stock\Item;
 
+/**
+ * Products mass update inventory tab
+ */
 class Inventory extends \Magento\Backend\Block\Widget implements \Magento\Backend\Block\Widget\Tab\TabInterface
 {
     /**
@@ -91,7 +89,11 @@ class Inventory extends \Magento\Backend\Block\Widget implements \Magento\Backen
      */
     public function getDefaultConfigValue($field)
     {
-        return $this->_scopeConfig->getValue(Item::XML_PATH_ITEM . $field, \Magento\Store\Model\ScopeInterface::SCOPE_STORE, $this->getStoreId());
+        return $this->_scopeConfig->getValue(
+            Item::XML_PATH_ITEM . $field,
+            \Magento\Store\Model\ScopeInterface::SCOPE_STORE,
+            $this->getStoreId()
+        );
     }
 
     /**
diff --git a/app/code/Magento/Catalog/Block/Adminhtml/Product/Edit/Tab/Inventory.php b/app/code/Magento/Catalog/Block/Adminhtml/Product/Edit/Tab/Inventory.php
index 9d2478b5560..49e90dcd850 100644
--- a/app/code/Magento/Catalog/Block/Adminhtml/Product/Edit/Tab/Inventory.php
+++ b/app/code/Magento/Catalog/Block/Adminhtml/Product/Edit/Tab/Inventory.php
@@ -25,8 +25,6 @@ namespace Magento\Catalog\Block\Adminhtml\Product\Edit\Tab;
 
 /**
  * Product inventory data
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
 class Inventory extends \Magento\Backend\Block\Widget
 {
@@ -40,14 +38,14 @@ class Inventory extends \Magento\Backend\Block\Widget
      *
      * @var \Magento\Catalog\Helper\Data
      */
-    protected $_catalogData = null;
+    protected $_catalogData;
 
     /**
      * Core registry
      *
      * @var \Magento\Framework\Registry
      */
-    protected $_coreRegistry = null;
+    protected $_coreRegistry;
 
     /**
      * @var \Magento\CatalogInventory\Model\Source\Stock
@@ -138,7 +136,10 @@ class Inventory extends \Magento\Backend\Block\Widget
             return $this->getStockItem()->getDataUsingMethod($field);
         }
 
-        return $this->_scopeConfig->getValue(\Magento\CatalogInventory\Model\Stock\Item::XML_PATH_ITEM . $field, \Magento\Store\Model\ScopeInterface::SCOPE_STORE);
+        return $this->_scopeConfig->getValue(
+            \Magento\CatalogInventory\Model\Stock\Item::XML_PATH_ITEM . $field,
+            \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+        );
     }
 
     /**
@@ -153,7 +154,10 @@ class Inventory extends \Magento\Backend\Block\Widget
             }
         }
 
-        return $this->_scopeConfig->getValue(\Magento\CatalogInventory\Model\Stock\Item::XML_PATH_ITEM . $field, \Magento\Store\Model\ScopeInterface::SCOPE_STORE);
+        return $this->_scopeConfig->getValue(
+            \Magento\CatalogInventory\Model\Stock\Item::XML_PATH_ITEM . $field,
+            \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+        );
     }
 
     /**
@@ -162,7 +166,10 @@ class Inventory extends \Magento\Backend\Block\Widget
      */
     public function getDefaultConfigValue($field)
     {
-        return $this->_scopeConfig->getValue(\Magento\CatalogInventory\Model\Stock\Item::XML_PATH_ITEM . $field, \Magento\Store\Model\ScopeInterface::SCOPE_STORE);
+        return $this->_scopeConfig->getValue(
+            \Magento\CatalogInventory\Model\Stock\Item::XML_PATH_ITEM . $field,
+            \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+        );
     }
 
     /**
diff --git a/app/code/Magento/Catalog/Block/Product/AbstractProduct.php b/app/code/Magento/Catalog/Block/Product/AbstractProduct.php
index c6f1f68b2c1..1ec50c29083 100644
--- a/app/code/Magento/Catalog/Block/Product/AbstractProduct.php
+++ b/app/code/Magento/Catalog/Block/Product/AbstractProduct.php
@@ -21,17 +21,10 @@
  * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
-
-
-/**
- * Catalog Product Abstract Block
- *
- * @author     Magento Core Team <core@magentocommerce.com>
- */
 namespace Magento\Catalog\Block\Product;
 
 /**
- * Class AbstractProduct
+ * Catalog Product Abstract Block
  */
 abstract class AbstractProduct extends \Magento\Framework\View\Element\Template
 {
@@ -85,21 +78,21 @@ abstract class AbstractProduct extends \Magento\Framework\View\Element\Template
      *
      * @var \Magento\Framework\Registry
      */
-    protected $_coreRegistry = null;
+    protected $_coreRegistry;
 
     /**
      * Catalog data
      *
      * @var \Magento\Catalog\Helper\Data
      */
-    protected $_catalogData = null;
+    protected $_catalogData;
 
     /**
      * Tax data
      *
      * @var \Magento\Tax\Helper\Data
      */
-    protected $_taxData = null;
+    protected $_taxData;
 
     /**
      * Catalog config
@@ -143,6 +136,11 @@ abstract class AbstractProduct extends \Magento\Framework\View\Element\Template
      */
     protected $reviewRenderer;
 
+    /**
+     * @var \Magento\CatalogInventory\Service\V1\StockItem
+     */
+    protected $stockItemService;
+
     /**
      * @param Context $context
      * @param array $data
@@ -162,6 +160,7 @@ abstract class AbstractProduct extends \Magento\Framework\View\Element\Template
         $this->_catalogData = $context->getCatalogHelper();
         $this->_mathRandom = $context->getMathRandom();
         $this->reviewRenderer = $context->getReviewRenderer();
+        $this->stockItemService = $context->getStockItemService();
         parent::__construct($context, $data);
     }
 
@@ -190,8 +189,9 @@ abstract class AbstractProduct extends \Magento\Framework\View\Element\Template
     }
 
     /**
-     * Retrieves url for form submitting:
-     * some objects can use setSubmitRouteData() to set route and params for form submitting,
+     * Retrieves url for form submitting.
+     *
+     * Some objects can use setSubmitRouteData() to set route and params for form submitting,
      * otherwise default url will be used
      *
      * @param \Magento\Catalog\Model\Product $product
@@ -240,12 +240,8 @@ abstract class AbstractProduct extends \Magento\Framework\View\Element\Template
      */
     public function getMinimalQty($product)
     {
-        $stockItem = $product->getStockItem();
-        if ($stockItem) {
-            return $stockItem->getMinSaleQty()
-                && $stockItem->getMinSaleQty() > 0 ? $stockItem->getMinSaleQty() * 1 : null;
-        }
-        return null;
+        $minSaleQty = $this->stockItemService->getMinSaleQty($product->getId());
+        return $minSaleQty > 0 ? $minSaleQty : null;
     }
 
     /**
@@ -259,19 +255,19 @@ abstract class AbstractProduct extends \Magento\Framework\View\Element\Template
      */
     public function getPriceHtml($product, $displayMinimalPrice = false, $idSuffix = '')
     {
-        $type_id = $product->getTypeId();
+        $typeId = $product->getTypeId();
         if ($this->_catalogData->canApplyMsrp($product)) {
-            $realPriceHtml = $this->_preparePriceRenderer($type_id)
+            $realPriceHtml = $this->_preparePriceRenderer($typeId)
                 ->setProduct($product)
                 ->setDisplayMinimalPrice($displayMinimalPrice)
                 ->setIdSuffix($idSuffix)
                 ->toHtml();
             $product->setAddToCartUrl($this->getAddToCartUrl($product));
             $product->setRealPriceHtml($realPriceHtml);
-            $type_id = $this->_mapRenderer;
+            $typeId = $this->_mapRenderer;
         }
 
-        return $this->_preparePriceRenderer($type_id)
+        return $this->_preparePriceRenderer($typeId)
             ->setProduct($product)
             ->setDisplayMinimalPrice($displayMinimalPrice)
             ->setIdSuffix($idSuffix)
@@ -664,11 +660,7 @@ abstract class AbstractProduct extends \Magento\Framework\View\Element\Template
         $price = '';
 
         if ($priceRender) {
-            $price = $priceRender->render(
-                $priceType,
-                $product,
-                $arguments
-            );
+            $price = $priceRender->render($priceType, $product, $arguments);
         }
         return $price;
     }
diff --git a/app/code/Magento/Catalog/Block/Product/Context.php b/app/code/Magento/Catalog/Block/Product/Context.php
index 4abf2def9af..8f23e8f9b54 100644
--- a/app/code/Magento/Catalog/Block/Product/Context.php
+++ b/app/code/Magento/Catalog/Block/Product/Context.php
@@ -23,6 +23,9 @@
  */
 namespace Magento\Catalog\Block\Product;
 
+/**
+ * Abstract product block context
+ */
 class Context extends \Magento\Framework\View\Element\Template\Context
 {
     /**
@@ -80,6 +83,11 @@ class Context extends \Magento\Framework\View\Element\Template\Context
      */
     protected $reviewRenderer;
 
+    /**
+     * @var \Magento\CatalogInventory\Service\V1\StockItem
+     */
+    protected $stockItemService;
+
     /**
      * @param \Magento\Framework\App\RequestInterface $request
      * @param \Magento\Framework\View\LayoutInterface $layout
@@ -115,6 +123,7 @@ class Context extends \Magento\Framework\View\Element\Template\Context
      * @param \Magento\Theme\Helper\Layout $layoutHelper
      * @param \Magento\Catalog\Helper\Image $imageHelper
      * @param ReviewRendererInterface $reviewRenderer
+     * @param \Magento\CatalogInventory\Service\V1\StockItem $stockItemService
      *
      * @SuppressWarnings(PHPMD.ExcessiveParameterList)
      */
@@ -152,7 +161,8 @@ class Context extends \Magento\Framework\View\Element\Template\Context
         \Magento\Catalog\Helper\Product\Compare $compareProduct,
         \Magento\Theme\Helper\Layout $layoutHelper,
         \Magento\Catalog\Helper\Image $imageHelper,
-        ReviewRendererInterface $reviewRenderer
+        ReviewRendererInterface $reviewRenderer,
+        \Magento\CatalogInventory\Service\V1\StockItem $stockItemService
     ) {
         $this->imageHelper = $imageHelper;
         $this->layoutHelper = $layoutHelper;
@@ -165,6 +175,7 @@ class Context extends \Magento\Framework\View\Element\Template\Context
         $this->catalogHelper = $catalogHelper;
         $this->mathRandom = $mathRandom;
         $this->reviewRenderer = $reviewRenderer;
+        $this->stockItemService = $stockItemService;
         parent::__construct(
             $request,
             $layout,
@@ -192,6 +203,14 @@ class Context extends \Magento\Framework\View\Element\Template\Context
         );
     }
 
+    /**
+     * @return \Magento\CatalogInventory\Service\V1\StockItem
+     */
+    public function getStockItemService()
+    {
+        return $this->stockItemService;
+    }
+
     /**
      * @return \Magento\Checkout\Helper\Cart
      */
diff --git a/app/code/Magento/Catalog/Block/Product/View.php b/app/code/Magento/Catalog/Block/Product/View.php
index a4f38ccf646..546eaa128f4 100644
--- a/app/code/Magento/Catalog/Block/Product/View.php
+++ b/app/code/Magento/Catalog/Block/Product/View.php
@@ -236,15 +236,15 @@ class View extends AbstractProduct implements \Magento\Framework\View\Block\Iden
             return $this->_jsonEncoder->encode($config);
         }
 
-        $_request = $this->_taxCalculation->getRateRequest(false, false, false);
+        $request = $this->_taxCalculation->getRateRequest(false, false, false);
         /* @var $product \Magento\Catalog\Model\Product */
         $product = $this->getProduct();
-        $_request->setProductClassId($product->getTaxClassId());
-        $defaultTax = $this->_taxCalculation->getRate($_request);
+        $request->setProductClassId($product->getTaxClassId());
+        $defaultTax = $this->_taxCalculation->getRate($request);
 
-        $_request = $this->_taxCalculation->getRateRequest();
-        $_request->setProductClassId($product->getTaxClassId());
-        $currentTax = $this->_taxCalculation->getRate($_request);
+        $request = $this->_taxCalculation->getRateRequest();
+        $request->setProductClassId($product->getTaxClassId());
+        $currentTax = $this->_taxCalculation->getRate($request);
 
         $tierPrices = array();
 
diff --git a/app/code/Magento/Catalog/Controller/Adminhtml/Product/Action/Attribute.php b/app/code/Magento/Catalog/Controller/Adminhtml/Product/Action/Attribute.php
index 706bfa36892..102e33268f7 100644
--- a/app/code/Magento/Catalog/Controller/Adminhtml/Product/Action/Attribute.php
+++ b/app/code/Magento/Catalog/Controller/Adminhtml/Product/Action/Attribute.php
@@ -27,8 +27,6 @@ use Magento\Backend\App\Action;
 
 /**
  * Adminhtml catalog product action attribute update controller
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
 class Attribute extends Action
 {
@@ -47,7 +45,7 @@ class Attribute extends Action
      *
      * @var \Magento\Catalog\Helper\Product
      */
-    protected $_catalogProduct = null;
+    protected $_catalogProduct;
 
     /**
      * @param Action\Context $context
@@ -110,20 +108,13 @@ class Attribute extends Action
 
         try {
             if ($attributesData) {
-                $dateFormat = $this->_objectManager->get(
-                    'Magento\Framework\Stdlib\DateTime\TimezoneInterface'
-                )->getDateFormat(
-                    \Magento\Framework\Stdlib\DateTime\TimezoneInterface::FORMAT_TYPE_SHORT
-                );
+                $dateFormat = $this->_objectManager->get('Magento\Framework\Stdlib\DateTime\TimezoneInterface')
+                    ->getDateFormat(\Magento\Framework\Stdlib\DateTime\TimezoneInterface::FORMAT_TYPE_SHORT);
                 $storeId = $this->_helper->getSelectedStoreId();
 
                 foreach ($attributesData as $attributeCode => $value) {
-                    $attribute = $this->_objectManager->get(
-                        'Magento\Eav\Model\Config'
-                    )->getAttribute(
-                        \Magento\Catalog\Model\Product::ENTITY,
-                        $attributeCode
-                    );
+                    $attribute = $this->_objectManager->get('Magento\Eav\Model\Config')
+                        ->getAttribute(\Magento\Catalog\Model\Product::ENTITY, $attributeCode);
                     if (!$attribute->getAttributeId()) {
                         unset($attributesData[$attributeCode]);
                         continue;
@@ -141,7 +132,7 @@ class Attribute extends Action
                         $attributesData[$attributeCode] = $value;
                     } elseif ($attribute->getFrontendInput() == 'multiselect') {
                         // Check if 'Change' checkbox has been checked by admin for this attribute
-                        $isChanged = (bool)$this->getRequest()->getPost($attributeCode . '_checkbox');
+                        $isChanged = (bool) $this->getRequest()->getPost($attributeCode . '_checkbox');
                         if (!$isChanged) {
                             unset($attributesData[$attributeCode]);
                             continue;
@@ -153,13 +144,8 @@ class Attribute extends Action
                     }
                 }
 
-                $this->_objectManager->get(
-                    'Magento\Catalog\Model\Product\Action'
-                )->updateAttributes(
-                    $this->_helper->getProductIds(),
-                    $attributesData,
-                    $storeId
-                );
+                $this->_objectManager->get('Magento\Catalog\Model\Product\Action')
+                    ->updateAttributes($this->_helper->getProductIds(), $attributesData, $storeId);
             }
             if ($inventoryData) {
                 $stockItem = $this->_objectManager->create('Magento\CatalogInventory\Model\Stock\Item');
@@ -184,9 +170,7 @@ class Attribute extends Action
                 }
 
                 if ($stockItemSaved) {
-                    $this->_objectManager->get(
-                        'Magento\Index\Model\Indexer'
-                    )->indexEvents(
+                    $this->_objectManager->get('Magento\Index\Model\Indexer')->indexEvents(
                         \Magento\CatalogInventory\Model\Stock\Item::ENTITY,
                         \Magento\Index\Model\Event::TYPE_SAVE
                     );
@@ -222,9 +206,9 @@ class Attribute extends Action
 
             $this->_productFlatIndexerProcessor->reindexList($this->_helper->getProductIds());
 
-            if ($this->_catalogProduct->isDataForPriceIndexerWasChanged(
-                $attributesData
-            ) || !empty($websiteRemoveData) || !empty($websiteAddData)
+            if ($this->_catalogProduct->isDataForPriceIndexerWasChanged($attributesData)
+                || !empty($websiteRemoveData)
+                || !empty($websiteAddData)
             ) {
                 $this->_productPriceIndexerProcessor->reindexList($this->_helper->getProductIds());
             }
@@ -251,7 +235,7 @@ class Attribute extends Action
         $productIds = $this->_helper->getProductIds();
         if (!is_array($productIds)) {
             $error = __('Please select products for attributes update.');
-        } else if (!$this->_objectManager->create('Magento\Catalog\Model\Product')->isProductsHasSku($productIds)) {
+        } elseif (!$this->_objectManager->create('Magento\Catalog\Model\Product')->isProductsHasSku($productIds)) {
             $error = __('Please make sure to define SKU values for all processed products.');
         }
 
@@ -286,12 +270,8 @@ class Attribute extends Action
         try {
             if ($attributesData) {
                 foreach ($attributesData as $attributeCode => $value) {
-                    $attribute = $this->_objectManager->get(
-                        'Magento\Eav\Model\Config'
-                    )->getAttribute(
-                        'catalog_product',
-                        $attributeCode
-                    );
+                    $attribute = $this->_objectManager->get('Magento\Eav\Model\Config')
+                        ->getAttribute('catalog_product', $attributeCode);
                     if (!$attribute->getAttributeId()) {
                         unset($attributesData[$attributeCode]);
                         continue;
diff --git a/app/code/Magento/Catalog/Model/Product/Attribute/Backend/Sku.php b/app/code/Magento/Catalog/Model/Product/Attribute/Backend/Sku.php
index 0fe4915decd..a97a2a7ca01 100644
--- a/app/code/Magento/Catalog/Model/Product/Attribute/Backend/Sku.php
+++ b/app/code/Magento/Catalog/Model/Product/Attribute/Backend/Sku.php
@@ -68,8 +68,8 @@ class Sku extends \Magento\Eav\Model\Entity\Attribute\Backend\AbstractBackend
     {
         $attrCode = $this->getAttribute()->getAttributeCode();
         $value = $object->getData($attrCode);
-        if ($this->getAttribute()->getIsRequired() && $this->getAttribute()->isValueEmpty($value)) {
-            return false;
+        if ($this->getAttribute()->getIsRequired() && strlen($value) === 0) {
+            throw new \Magento\Eav\Exception(__('The value of attribute "%1" must be set', $attrCode));
         }
 
         if ($this->string->strlen($object->getSku()) > self::SKU_MAX_LENGTH) {
diff --git a/app/code/Magento/Catalog/Model/Product/Attribute/Backend/Stock.php b/app/code/Magento/Catalog/Model/Product/Attribute/Backend/Stock.php
index f55352e67b6..f82734a2e95 100644
--- a/app/code/Magento/Catalog/Model/Product/Attribute/Backend/Stock.php
+++ b/app/code/Magento/Catalog/Model/Product/Attribute/Backend/Stock.php
@@ -22,16 +22,13 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-
-/**
- * Quantity and Stock Status attribute processing
- *
- * @author     Magento Core Team <core@magentocommerce.com>
- */
 namespace Magento\Catalog\Model\Product\Attribute\Backend;
 
 use Magento\Catalog\Model\Product;
 
+/**
+ * Quantity and Stock Status attribute processing
+ */
 class Stock extends \Magento\Eav\Model\Entity\Attribute\Backend\AbstractBackend
 {
     /**
diff --git a/app/code/Magento/Catalog/Model/Product/Type/AbstractType.php b/app/code/Magento/Catalog/Model/Product/Type/AbstractType.php
index 92322c5af12..902ef537358 100644
--- a/app/code/Magento/Catalog/Model/Product/Type/AbstractType.php
+++ b/app/code/Magento/Catalog/Model/Product/Type/AbstractType.php
@@ -21,14 +21,11 @@
  * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
+namespace Magento\Catalog\Model\Product\Type;
 
 /**
  * Abstract model for product type implementation
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
-namespace Magento\Catalog\Model\Product\Type;
-
 abstract class AbstractType
 {
     /**
@@ -76,13 +73,13 @@ abstract class AbstractType
 
     const CALCULATE_PARENT = 1;
 
-    /**
+    /**#@+
      * values for shipment type (invoice etc)
-     *
      */
     const SHIPMENT_SEPARATELY = 1;
 
     const SHIPMENT_TOGETHER = 0;
+    /**#@-*/
 
     /**
      * Process modes
@@ -132,14 +129,14 @@ abstract class AbstractType
      *
      * @var \Magento\Framework\Registry
      */
-    protected $_coreRegistry = null;
+    protected $_coreRegistry;
 
     /**
      * Core event manager proxy
      *
      * @var \Magento\Framework\Event\ManagerInterface
      */
-    protected $_eventManager = null;
+    protected $_eventManager;
 
     /**
      * @var \Magento\Framework\Logger
@@ -270,11 +267,9 @@ abstract class AbstractType
      */
     public function getSetAttributes($product)
     {
-        return $product->getResource()->loadAllAttributes(
-            $product
-        )->getSortedAttributes(
-            $product->getAttributeSetId()
-        );
+        return $product->getResource()
+            ->loadAllAttributes($product)
+            ->getSortedAttributes($product->getAttributeSetId());
     }
 
     /**
@@ -440,13 +435,14 @@ abstract class AbstractType
      * @param string $processMode
      * @return array|string
      */
-    public function processConfiguration(\Magento\Framework\Object $buyRequest, $product, $processMode = self::PROCESS_MODE_LITE)
-    {
-        $_products = $this->_prepareProduct($buyRequest, $product, $processMode);
-
+    public function processConfiguration(
+        \Magento\Framework\Object $buyRequest,
+        $product,
+        $processMode = self::PROCESS_MODE_LITE
+    ) {
+        $products = $this->_prepareProduct($buyRequest, $product, $processMode);
         $this->processFileQueue();
-
-        return $_products;
+        return $products;
     }
 
     /**
@@ -583,25 +579,18 @@ abstract class AbstractType
     {
         $transport = new \StdClass();
         $transport->options = array();
-        foreach ($product->getOptions() as $_option) {
-            /* @var $_option \Magento\Catalog\Model\Product\Option */
-            $group = $_option->groupFactory(
-                $_option->getType()
-            )->setOption(
-                $_option
-            )->setProduct(
-                $product
-            )->setRequest(
-                $buyRequest
-            )->setProcessMode(
-                $processMode
-            )->validateUserValue(
-                $buyRequest->getOptions()
-            );
+        foreach ($product->getOptions() as $option) {
+            /* @var $option \Magento\Catalog\Model\Product\Option */
+            $group = $option->groupFactory($option->getType())
+                ->setOption($option)
+                ->setProduct($product)
+                ->setRequest($buyRequest)
+                ->setProcessMode($processMode)
+                ->validateUserValue($buyRequest->getOptions());
 
             $preparedValue = $group->prepareForCart();
             if ($preparedValue !== null) {
-                $transport->options[$_option->getId()] = $preparedValue;
+                $transport->options[$option->getId()] = $preparedValue;
             }
         }
 
@@ -659,15 +648,10 @@ abstract class AbstractType
                 if ($option) {
                     $confItemOption = $product->getCustomOption(self::OPTION_PREFIX . $option->getId());
 
-                    $group = $option->groupFactory(
-                        $option->getType()
-                    )->setOption(
-                        $option
-                    )->setProduct(
-                        $product
-                    )->setConfigurationItemOption(
-                        $confItemOption
-                    );
+                    $group = $option->groupFactory($option->getType())
+                        ->setOption($option)
+                        ->setProduct($product)
+                        ->setConfigurationItemOption($confItemOption);
 
                     $optionArr['options'][] = array(
                         'label' => $option->getTitle(),
@@ -812,13 +796,9 @@ abstract class AbstractType
 
                     $confItemOption = $product->getCustomOption(self::OPTION_PREFIX . $optionId);
 
-                    $group = $option->groupFactory(
-                        $option->getType()
-                    )->setOption(
-                        $option
-                    )->setListener(
-                        new \Magento\Framework\Object()
-                    );
+                    $group = $option->groupFactory($option->getType())
+                        ->setOption($option)
+                        ->setListener(new \Magento\Framework\Object());
 
                     $optionSku = $group->getOptionSku($confItemOption->getValue(), $skuDelimiter);
                     if ($optionSku) {
@@ -971,7 +951,7 @@ abstract class AbstractType
         }
 
         if (isset($config['can_use_qty_decimals'])) {
-            $this->_canUseQtyDecimals = (bool)$config['can_use_qty_decimals'];
+            $this->_canUseQtyDecimals = (bool) $config['can_use_qty_decimals'];
         }
 
         return $this;
diff --git a/app/code/Magento/Catalog/Model/Product/Type/Simple.php b/app/code/Magento/Catalog/Model/Product/Type/Simple.php
index 4a41b188cba..895f1fd2040 100644
--- a/app/code/Magento/Catalog/Model/Product/Type/Simple.php
+++ b/app/code/Magento/Catalog/Model/Product/Type/Simple.php
@@ -21,14 +21,11 @@
  * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
+namespace Magento\Catalog\Model\Product\Type;
 
 /**
  * Simple product type implementation
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
-namespace Magento\Catalog\Model\Product\Type;
-
 class Simple extends \Magento\Catalog\Model\Product\Type\AbstractType
 {
     /**
diff --git a/app/code/Magento/Catalog/Model/Resource/Product/Link/Product/Collection.php b/app/code/Magento/Catalog/Model/Resource/Product/Link/Product/Collection.php
index 7c6010631ed..6fa34b62577 100644
--- a/app/code/Magento/Catalog/Model/Resource/Product/Link/Product/Collection.php
+++ b/app/code/Magento/Catalog/Model/Resource/Product/Link/Product/Collection.php
@@ -112,6 +112,7 @@ class Collection extends \Magento\Catalog\Model\Resource\Product\Collection
         $this->_product = $product;
         if ($product && $product->getId()) {
             $this->_hasLinkFilter = true;
+            $this->setStore($product->getStore());
         }
         return $this;
     }
diff --git a/app/code/Magento/Catalog/Service/V1/Data/Converter.php b/app/code/Magento/Catalog/Service/V1/Data/Converter.php
new file mode 100644
index 00000000000..57dc8d19b55
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/Converter.php
@@ -0,0 +1,85 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data;
+
+use Magento\Catalog\Service\V1\Data\ProductBuilder;
+use Magento\Catalog\Service\V1\Data\Product as ProductDataObject;
+
+/**
+ * Product Model converter.
+ *
+ * Converts a Product Model to a Data Object or vice versa.
+ */
+class Converter
+{
+    /**
+     * @var ProductBuilder
+     */
+    protected $productBuilder;
+
+    /**
+     * @param ProductBuilder $productBuilder
+     */
+    public function __construct(ProductBuilder $productBuilder)
+    {
+        $this->productBuilder = $productBuilder;
+    }
+
+    /**
+     * Convert a product model to a product data entity
+     *
+     * @param \Magento\Catalog\Model\Product $productModel
+     * @return \Magento\Catalog\Service\V1\Data\Product
+     */
+    public function createProductDataFromModel(\Magento\Catalog\Model\Product $productModel)
+    {
+        $this->_populateBuilderWithAttributes($productModel);
+        return $this->productBuilder->create();
+    }
+
+    /**
+     * Loads the values from a product model
+     *
+     * @param \Magento\Catalog\Model\Product $productModel
+     * @return void
+     */
+    protected function _populateBuilderWithAttributes(\Magento\Catalog\Model\Product $productModel)
+    {
+        $attributes = array();
+        foreach ($this->productBuilder->getCustomAttributesCodes() as $attrCode) {
+            $value = $productModel->getDataUsingMethod($attrCode);
+            $value = $value ? $value : $productModel->getData($attrCode);
+            if (null !== $value) {
+                if ($attrCode == 'entity_id') {
+                    $attributes[ProductDataObject::ID] = $value;
+                } else {
+                    $attributes[$attrCode] = $value;
+                }
+            }
+        }
+
+        $this->productBuilder->populateWithArray($attributes);
+        return;
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadata.php b/app/code/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadata.php
new file mode 100644
index 00000000000..5606c3f7b04
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadata.php
@@ -0,0 +1,393 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data\Eav;
+
+/**
+ * Class AttributeMetadata
+ */
+class AttributeMetadata extends \Magento\Framework\Service\Data\AbstractObject
+{
+    /**#@+
+     * Constants used as keys into $_data
+     */
+    const ATTRIBUTE_ID = 'attribute_id';
+
+    const ATTRIBUTE_CODE = 'attribute_code';
+
+    const FRONTEND_INPUT = 'frontend_input';
+
+    const VALIDATION_RULES = 'validation_rules';
+
+    const OPTIONS = 'options';
+
+    const VISIBLE = 'visible';
+
+    const REQUIRED = 'required';
+
+    const USER_DEFINED = 'user_defined';
+
+    const FRONTEND_LABEL = 'frontend_label';
+
+    const NOTE = 'note';
+
+    const BACKEND_TYPE = 'backend_type';
+
+    const DEFAULT_VALUE = 'default_value';
+
+    const UNIQUE = 'unique';
+
+    const APPLY_TO = 'apply_to';
+
+    const CONFIGURABLE = 'configurable';
+
+    const SEARCHABLE = 'searchable';
+
+    const VISIBLE_IN_ADVANCED_SEARCH = 'visible_in_advanced_search';
+
+    const COMPARABLE = 'comparable';
+
+    const USED_FOR_PROMO_RULES = 'used_for_promo_rules';
+
+    const VISIBLE_ON_FRONT = 'visible_on_front';
+
+    const USED_IN_PRODUCT_LISTING = 'used_in_product_listing';
+
+    const SCOPE = 'scope';
+
+    // additional fields
+    const WYSIWYG_ENABLED = 'wysiwyg_enabled';
+
+    const HTML_ALLOWED_ON_FRONT = 'html_allowed_on_front';
+
+    const FRONTEND_CLASS = 'frontend_class';
+
+    const USED_FOR_SORT_BY = 'used_for_sort_by';
+
+    const FILTERABLE = 'filterable';
+
+    const FILTERABLE_IN_SEARCH = 'filterable_in_search';
+
+    const POSITION = 'position';
+    /**#@-*/
+
+    /**
+     * Retrieve id of the attribute.
+     *
+     * @return string
+     */
+    public function getAttributeId()
+    {
+        return $this->_get(self::ATTRIBUTE_ID);
+    }
+
+    /**
+     * Retrieve code of the attribute.
+     *
+     * @return string
+     */
+    public function getAttributeCode()
+    {
+        return $this->_get(self::ATTRIBUTE_CODE);
+    }
+
+    /**
+     * Frontend HTML for input element.
+     *
+     * @return string
+     */
+    public function getFrontendInput()
+    {
+        return $this->_get(self::FRONTEND_INPUT);
+    }
+
+    /**
+     * Retrieve validation rules.
+     *
+     * @return \Magento\Catalog\Service\V1\Data\Eav\ValidationRule[]
+     */
+    public function getValidationRules()
+    {
+        return $this->_get(self::VALIDATION_RULES);
+    }
+
+    /**
+     * Whether attribute is visible on frontend.
+     *
+     * @return bool
+     */
+    public function isVisible()
+    {
+        return $this->_get(self::VISIBLE);
+    }
+
+    /**
+     * Whether attribute is required.
+     *
+     * @return bool
+     */
+    public function isRequired()
+    {
+        return $this->_get(self::REQUIRED);
+    }
+
+    /**
+     * Return options of the attribute (key => value pairs for select)
+     *
+     * @return \Magento\Catalog\Service\V1\Data\Eav\Option[]
+     */
+    public function getOptions()
+    {
+        return $this->_get(self::OPTIONS);
+    }
+
+    /**
+     * Whether current attribute has been defined by a user.
+     *
+     * @return bool
+     */
+    public function isUserDefined()
+    {
+        return $this->_get(self::USER_DEFINED);
+    }
+
+    /**
+     * Get label which supposed to be displayed on frontend.
+     *
+     * @return string
+     */
+    public function getFrontendLabel()
+    {
+        return $this->_get(self::FRONTEND_LABEL);
+    }
+
+    /**
+     * Get the note attribute for the element.
+     *
+     * @return string
+     */
+    public function getNote()
+    {
+        return $this->_get(self::NOTE);
+    }
+
+    /**
+     * Get backend type.
+     *
+     * @return string
+     */
+    public function getBackendType()
+    {
+        return $this->_get(self::BACKEND_TYPE);
+    }
+
+    /**
+     * Get default value for the element.
+     *
+     * @return string
+     */
+    public function getDefaultValue()
+    {
+        return $this->_get(self::DEFAULT_VALUE);
+    }
+
+    /**
+     * Whether this is a unique attribute
+     *
+     * @return string
+     */
+    public function isUnique()
+    {
+        return $this->_get(self::UNIQUE);
+    }
+
+    /**
+     * Get apply to value for the element
+     *
+     * Apply to. Empty for "Apply to all"
+     * or array of the following possible values:
+     *  - 'simple',
+     *  - 'grouped',
+     *  - 'configurable',
+     *  - 'virtual',
+     *  - 'bundle',
+     *  - 'downloadable'
+     *
+     * @return string[]
+     */
+    public function getApplyTo()
+    {
+        return $this->_get(self::APPLY_TO);
+    }
+
+    /**
+     * Whether the attribute can be used for configurable products
+     *
+     * @return string
+     */
+    public function isConfigurable()
+    {
+        return $this->_get(self::CONFIGURABLE);
+    }
+
+    /**
+     * Whether the attribute can be used in Quick Search
+     *
+     * @return string
+     */
+    public function isSearchable()
+    {
+        return $this->_get(self::SEARCHABLE);
+    }
+
+    /**
+     * Whether the attribute can be used in Advanced Search
+     *
+     * @return string
+     */
+    public function isVisibleInAdvancedSearch()
+    {
+        return $this->_get(self::VISIBLE_IN_ADVANCED_SEARCH);
+    }
+
+    /**
+     * Whether the attribute can be compared on the frontend
+     *
+     * @return string
+     */
+    public function isComparable()
+    {
+        return $this->_get(self::COMPARABLE);
+    }
+
+    /**
+     * Whether the attribute can be used for promo rules
+     *
+     * @return string
+     */
+    public function isUsedForPromoRules()
+    {
+        return $this->_get(self::USED_FOR_PROMO_RULES);
+    }
+
+    /**
+     * Whether the attribute is visible on the frontend
+     *
+     * @return string
+     */
+    public function isVisibleOnFront()
+    {
+        return $this->_get(self::VISIBLE_ON_FRONT);
+    }
+
+    /**
+     * Whether the attribute can be used in product listing
+     *
+     * @return string
+     */
+    public function getUsedInProductListing()
+    {
+        return $this->_get(self::USED_IN_PRODUCT_LISTING);
+    }
+
+    /**
+     * Retrieve attribute scope
+     *
+     * @return string
+     */
+    public function getScope()
+    {
+        return $this->_get(self::SCOPE);
+    }
+
+    /**
+     * Retrieve frontend class of attribute
+     *
+     * @return string
+     */
+    public function getFrontendClass()
+    {
+        return $this->_get(self::FRONTEND_CLASS);
+    }
+
+    /**
+     * Enable WYSIWYG flag
+     *
+     * @return bool
+     */
+    public function isWysiwygEnabled()
+    {
+        return (bool)$this->_get(self::WYSIWYG_ENABLED);
+    }
+
+    /**
+     * Whether the HTML tags are allowed on the frontend
+     *
+     * @return bool
+     */
+    public function isHtmlAllowedOnFront()
+    {
+        return (bool)$this->_get(self::HTML_ALLOWED_ON_FRONT);
+    }
+
+    /**
+     * Whether it is used for sorting in product listing
+     *
+     * @return bool
+     * @SuppressWarnings(PHPMD.BooleanGetMethodName)
+     */
+    public function getUsedForSortBy()
+    {
+        return (bool)$this->_get(self::USED_FOR_SORT_BY);
+    }
+
+    /**
+     * Whether it used in layered navigation
+     *
+     * @return bool
+     */
+    public function isFilterable()
+    {
+        return (bool)$this->_get(self::FILTERABLE);
+    }
+
+    /**
+     * Whether it is used in search results layered navigation
+     *
+     * @return bool
+     */
+    public function isFilterableInSearch()
+    {
+        return (bool)$this->_get(self::FILTERABLE_IN_SEARCH);
+    }
+
+    /**
+     * Get position
+     *
+     * @return int
+     */
+    public function getPosition()
+    {
+        return (int)$this->_get(self::POSITION);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataBuilder.php b/app/code/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataBuilder.php
new file mode 100644
index 00000000000..3e996fa2ad3
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataBuilder.php
@@ -0,0 +1,441 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data\Eav;
+
+use Magento\Framework\Service\Data\AbstractObjectBuilder;
+use Magento\Eav\Model\Entity\Attribute\AbstractAttribute;
+
+/**
+ * Class AttributeMetadataBuilder
+ */
+class AttributeMetadataBuilder extends AbstractObjectBuilder
+{
+    /**
+     * Option builder
+     *
+     * @var OptionBuilder
+     */
+    protected $optionBuilder;
+
+    /**
+     * Validation rule builder
+     *
+     * @var ValidationRuleBuilder
+     */
+    protected $validationRuleBuilder;
+
+    /**
+     * Initializes builder.
+     *
+     * @param OptionBuilder $optionBuilder
+     * @param ValidationRuleBuilder $validationRuleBuilder
+     * @param \Magento\Framework\Service\Data\ObjectFactory $objectFactory
+     */
+    public function __construct(
+        \Magento\Framework\Service\Data\ObjectFactory $objectFactory,
+        OptionBuilder $optionBuilder,
+        ValidationRuleBuilder $validationRuleBuilder
+    ) {
+        parent::__construct($objectFactory);
+        $this->optionBuilder = $optionBuilder;
+        $this->validationRuleBuilder = $validationRuleBuilder;
+        $this->_data[AttributeMetadata::OPTIONS] = array();
+        $this->_data[AttributeMetadata::VALIDATION_RULES] = array();
+    }
+
+    /**
+     * Set attribute id
+     *
+     * @param  int $attributeId
+     * @return $this
+     */
+    public function setAttributeId($attributeId)
+    {
+        return $this->_set(AttributeMetadata::ATTRIBUTE_ID, $attributeId);
+    }
+
+    /**
+     * Set attribute code
+     *
+     * @param  string $attributeCode
+     * @return $this
+     */
+    public function setAttributeCode($attributeCode)
+    {
+        return $this->_set(AttributeMetadata::ATTRIBUTE_CODE, $attributeCode);
+    }
+
+    /**
+     * Set front end input
+     *
+     * @param  string $frontendInput
+     * @return $this
+     */
+    public function setFrontendInput($frontendInput)
+    {
+        return $this->_set(AttributeMetadata::FRONTEND_INPUT, $frontendInput);
+    }
+
+    /**
+     * Set validation rules
+     *
+     * @param  \Magento\Catalog\Service\V1\Data\Eav\ValidationRule[] $validationRules
+     * @return $this
+     */
+    public function setValidationRules($validationRules)
+    {
+        return $this->_set(AttributeMetadata::VALIDATION_RULES, $validationRules);
+    }
+
+    /**
+     * Set options
+     * 
+     * @param  \Magento\Catalog\Service\V1\Data\Eav\Option[] $options
+     * @return $this
+     */
+    public function setOptions($options)
+    {
+        return $this->_set(AttributeMetadata::OPTIONS, $options);
+    }
+
+    /**
+     * Set visible
+     *
+     * @param  bool $visible
+     * @return $this
+     */
+    public function setVisible($visible)
+    {
+        return $this->_set(AttributeMetadata::VISIBLE, $visible);
+    }
+
+    /**
+     * Set required
+     *
+     * @param  bool $required
+     * @return $this
+     */
+    public function setRequired($required)
+    {
+        return $this->_set(AttributeMetadata::REQUIRED, $required);
+    }
+
+    /**
+     * Set is user defined
+     *
+     * @param  bool $isUserDefined
+     * @return $this
+     */
+    public function setUserDefined($isUserDefined)
+    {
+        return $this->_set(AttributeMetadata::USER_DEFINED, $isUserDefined);
+    }
+
+    /**
+     * Set front end label
+     *
+     * @param  string $frontendLabel
+     * @return $this
+     */
+    public function setFrontendLabel($frontendLabel)
+    {
+        return $this->_set(AttributeMetadata::FRONTEND_LABEL, $frontendLabel);
+    }
+
+    /**
+     * Set note
+     *
+     * @param  string $note
+     * @return $this
+     */
+    public function setNote($note)
+    {
+        return $this->_set(AttributeMetadata::NOTE, $note);
+    }
+
+    /**
+     * @param  string $backendType
+     * @return AttributeMetadataBuilder
+     */
+    public function setBackendType($backendType)
+    {
+        return $this->_set(AttributeMetadata::BACKEND_TYPE, $backendType);
+    }
+
+    /**
+     * Set default value for the element
+     *
+     * @param  mixed $value
+     * @return $this
+     */
+    public function setDefaultValue($value)
+    {
+        return $this->_set(AttributeMetadata::DEFAULT_VALUE, $value);
+    }
+
+    /**
+     * Set whether this is a unique attribute
+     *
+     * @param  bool $isUnique
+     * @return $this
+     */
+    public function setUnique($isUnique)
+    {
+        return $this->_set(AttributeMetadata::UNIQUE, $isUnique);
+    }
+
+    /**
+     * Set apply to value for the element
+     *
+     * Apply to. Empty for "Apply to all"
+     * or array of the following possible values:
+     *  - 'simple',
+     *  - 'grouped',
+     *  - 'configurable',
+     *  - 'virtual',
+     *  - 'bundle',
+     *  - 'downloadable'
+     *
+     * @param  array|string|null $applyTo
+     * @return $this
+     */
+    public function setApplyTo($applyTo)
+    {
+        return $this->_set(AttributeMetadata::APPLY_TO, $this->processApplyToValue($applyTo));
+    }
+
+    /**
+     * Process applyTo value
+     *
+     * Transform string to array
+     *
+     * @param  string|array $applyTo
+     * @return array
+     */
+    protected function processApplyToValue($applyTo)
+    {
+        $value = array();
+        if (is_array($applyTo)) {
+            $value = $applyTo;
+        } elseif (is_string($applyTo)) {
+            $value = explode(',', $applyTo);
+        }
+        return $value;
+    }
+
+    /**
+     * Set whether the attribute can be used for configurable products
+     *
+     * @param  bool $isConfigurable
+     * @return $this
+     */
+    public function setConfigurable($isConfigurable)
+    {
+        return $this->_set(AttributeMetadata::CONFIGURABLE, $isConfigurable);
+    }
+
+    /**
+     * Set whether the attribute can be used in Quick Search
+     *
+     * @param  bool $isSearchable
+     * @return $this
+     */
+    public function setSearchable($isSearchable)
+    {
+        return $this->_set(AttributeMetadata::SEARCHABLE, $isSearchable);
+    }
+
+    /**
+     * Set whether the attribute can be used in Advanced Search
+     *
+     * @param  bool $isVisibleInAdvancedSearch
+     * @return $this
+     */
+    public function setVisibleInAdvancedSearch($isVisibleInAdvancedSearch)
+    {
+        return $this->_set(AttributeMetadata::VISIBLE_IN_ADVANCED_SEARCH, $isVisibleInAdvancedSearch);
+    }
+
+    /**
+     * Set whether the attribute can be compared on the frontend
+     *
+     * @param  bool $isComparable
+     * @return $this
+     */
+    public function setComparable($isComparable)
+    {
+        return $this->_set(AttributeMetadata::COMPARABLE, $isComparable);
+    }
+
+    /**
+     * Set whether the attribute can be used for promo rules
+     *
+     * @param  bool $isUsedForPromoRules
+     * @return $this
+     */
+    public function setUsedForPromoRules($isUsedForPromoRules)
+    {
+        return $this->_set(AttributeMetadata::USED_FOR_PROMO_RULES, $isUsedForPromoRules);
+    }
+
+    /**
+     * Set whether the attribute is visible on the frontend
+     *
+     * @param  bool $isVisibleOnFront
+     * @return $this
+     */
+    public function setVisibleOnFront($isVisibleOnFront)
+    {
+        return $this->_set(AttributeMetadata::VISIBLE_ON_FRONT, $isVisibleOnFront);
+    }
+
+    /**
+     * Set whether the attribute can be used in product listing
+     *
+     * @param  bool $usedInProductListing
+     * @return $this
+     */
+    public function setUsedInProductListing($usedInProductListing)
+    {
+        return $this->_set(AttributeMetadata::USED_IN_PRODUCT_LISTING, $usedInProductListing);
+    }
+
+    /**
+     * Set attribute scope value
+     *
+     * @param  string $scope
+     * @return $this
+     */
+    public function setScope($scope)
+    {
+        return $this->_set(AttributeMetadata::SCOPE, $scope);
+    }
+
+    /**
+     * Set whether it is used for sorting in product listing
+     *
+     * @param  bool $usedForSortBy
+     * @return $this
+     */
+    public function setUsedForSortBy($usedForSortBy)
+    {
+        return $this->_set(AttributeMetadata::USED_FOR_SORT_BY, (bool)$usedForSortBy);
+    }
+
+    /**
+     * Set whether it used in layered navigation
+     *
+     * @param  bool $isFilterable
+     * @return $this
+     */
+    public function setFilterable($isFilterable)
+    {
+        return $this->_set(AttributeMetadata::FILTERABLE, (bool)$isFilterable);
+    }
+
+    /**
+     * Set whether it is used in search results layered navigation
+     *
+     * @param  bool $isFilterableInSearch
+     * @return $this
+     */
+    public function setFilterableInSearch($isFilterableInSearch)
+    {
+        return $this->_set(AttributeMetadata::FILTERABLE_IN_SEARCH, (bool)$isFilterableInSearch);
+    }
+
+    /**
+     * Set position
+     *
+     * @param  int $position
+     * @return $this
+     */
+    public function setPosition($position)
+    {
+        return $this->_set(AttributeMetadata::POSITION, (int)$position);
+    }
+
+    /**
+     * Set whether WYSIWYG enabled or not
+     *
+     * @param  bool $isWysiwygEnabled
+     * @return $this
+     */
+    public function setWysiwygEnabled($isWysiwygEnabled)
+    {
+        return $this->_set(AttributeMetadata::WYSIWYG_ENABLED, (bool)$isWysiwygEnabled);
+    }
+
+    /**
+     * Set whether the HTML tags are allowed on the frontend
+     *
+     * @param  bool $isHtmlAllowedOnFront
+     * @return $this
+     */
+    public function setHtmlAllowedOnFront($isHtmlAllowedOnFront)
+    {
+        return $this->_set(AttributeMetadata::HTML_ALLOWED_ON_FRONT, (bool)$isHtmlAllowedOnFront);
+    }
+
+    /**
+     * Set frontend class for attribute
+     *
+     * @param  string $frontendClass
+     * @return $this
+     */
+    public function setFrontendClass($frontendClass)
+    {
+        return $this->_set(AttributeMetadata::FRONTEND_CLASS, $frontendClass);
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    protected function _setDataValues(array $data)
+    {
+        if (array_key_exists(AttributeMetadata::OPTIONS, $data)) {
+            $options = array();
+            if (is_array($data[AttributeMetadata::OPTIONS])) {
+                foreach ($data[AttributeMetadata::OPTIONS] as $key => $option) {
+                    $options[$key] = $this->optionBuilder->populateWithArray($option)->create();
+                }
+            }
+            $validationRules = array();
+            if (is_array($data[AttributeMetadata::VALIDATION_RULES])) {
+                foreach ($data[AttributeMetadata::VALIDATION_RULES] as $key => $value) {
+                    $validationRules[$key] = $this->validationRuleBuilder->populateWithArray($value)->create();
+                }
+            }
+
+            $data[AttributeMetadata::OPTIONS] = $options;
+            $data[AttributeMetadata::VALIDATION_RULES] = $validationRules;
+        }
+
+        if (array_key_exists(AttributeMetadata::APPLY_TO, $data)) {
+            $data[AttributeMetadata::APPLY_TO] = $this->processApplyToValue($data[AttributeMetadata::APPLY_TO]);
+        }
+
+        return parent::_setDataValues($data);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/Eav/Option.php b/app/code/Magento/Catalog/Service/V1/Data/Eav/Option.php
new file mode 100644
index 00000000000..4bb117b3697
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/Eav/Option.php
@@ -0,0 +1,59 @@
+<?php
+/**
+ * Eav attribute option
+ *
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data\Eav;
+
+/**
+ * Class Option
+ */
+class Option extends \Magento\Framework\Service\Data\AbstractObject
+{
+    /**
+     * Constants used as keys into $_data
+     */
+    const LABEL = 'label';
+
+    const VALUE = 'value';
+
+    /**
+     * Get option label
+     *
+     * @return string
+     */
+    public function getLabel()
+    {
+        return $this->_get(self::LABEL);
+    }
+
+    /**
+     * Get option value
+     *
+     * @return string
+     */
+    public function getValue()
+    {
+        return $this->_get(self::VALUE);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/Eav/OptionBuilder.php b/app/code/Magento/Catalog/Service/V1/Data/Eav/OptionBuilder.php
new file mode 100644
index 00000000000..893e33265e9
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/Eav/OptionBuilder.php
@@ -0,0 +1,52 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data\Eav;
+
+/**
+ * Class OptionBuilder
+ */
+class OptionBuilder extends \Magento\Framework\Service\Data\AbstractObjectBuilder
+{
+    /**
+     * Set option label
+     *
+     * @param  string $label
+     * @return $this
+     */
+    public function setLabel($label)
+    {
+        return $this->_set(Option::LABEL, $label);
+    }
+
+    /**
+     * Set option value
+     *
+     * @param  string $value
+     * @return $this
+     */
+    public function setValue($value)
+    {
+        return $this->_set(Option::VALUE, $value);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/Eav/ValidationRule.php b/app/code/Magento/Catalog/Service/V1/Data/Eav/ValidationRule.php
new file mode 100644
index 00000000000..58d5c41db20
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/Eav/ValidationRule.php
@@ -0,0 +1,54 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data\Eav;
+
+class ValidationRule extends \Magento\Framework\Service\Data\AbstractObject
+{
+    /**
+     * Constants used as keys into $_data
+     */
+    const NAME = 'name';
+
+    const VALUE = 'value';
+
+    /**
+     * Get validation rule name
+     *
+     * @return string
+     */
+    public function getName()
+    {
+        return $this->_get(self::NAME);
+    }
+
+    /**
+     * Get validation rule value
+     *
+     * @return string
+     */
+    public function getValue()
+    {
+        return $this->_get(self::VALUE);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/Eav/ValidationRuleBuilder.php b/app/code/Magento/Catalog/Service/V1/Data/Eav/ValidationRuleBuilder.php
new file mode 100644
index 00000000000..b4b92a48073
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/Eav/ValidationRuleBuilder.php
@@ -0,0 +1,49 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data\Eav;
+
+class ValidationRuleBuilder extends \Magento\Framework\Service\Data\AbstractObjectBuilder
+{
+    /**
+     * Set validation rule name
+     *
+     * @param  string $name
+     * @return $this
+     */
+    public function setName($name)
+    {
+        return $this->_set(ValidationRule::NAME, $name);
+    }
+
+    /**
+     * Set validation rule value
+     *
+     * @param  string $value
+     * @return $this
+     */
+    public function setValue($value)
+    {
+        return $this->_set(ValidationRule::VALUE, $value);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/Product.php b/app/code/Magento/Catalog/Service/V1/Data/Product.php
new file mode 100644
index 00000000000..73433ebe0d9
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/Product.php
@@ -0,0 +1,155 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data;
+
+/**
+ * Class Product
+ * @package Magento\Catalog\Service\V1\Data
+ */
+class Product extends \Magento\Framework\Service\Data\Eav\AbstractObject
+{
+    /**#@+
+     * Constants defined for keys of array
+     */
+    const ID = 'id';
+
+    const SKU = 'sku';
+
+    const NAME = 'name';
+
+    const PRICE = 'price';
+
+    const WEIGHT = 'weight';
+
+    const STATUS = 'status';
+
+    const ATTRIBUTE_SET_ID = 'attribute_set_id';
+
+    const VISIBILITY = 'visibility';
+
+    const TYPE_ID = 'type_id';
+
+    const CREATED_AT = 'created_at';
+
+    const UPDATED_AT = 'updated_at';
+
+    const STORE_ID = 'store_id';
+    /**#@-*/
+
+    /**
+     * @return int|null
+     */
+    public function getId()
+    {
+        return $this->_get(self::ID);
+    }
+
+    /**
+     * @return string|null
+     */
+    public function getSku()
+    {
+        return $this->_get(self::SKU);
+    }
+
+    /**
+     * @return string|null
+     */
+    public function getName()
+    {
+        return $this->_get(self::NAME);
+    }
+
+    /**
+     * @return int|null
+     */
+    public function getStoreId()
+    {
+        return $this->_get(self::STORE_ID);
+    }
+
+    /**
+     * @return int|null
+     */
+    public function getAttributeSetId()
+    {
+        return $this->_get(self::ATTRIBUTE_SET_ID);
+    }
+
+    /**
+     * @return float|null
+     */
+    public function getPrice()
+    {
+        return $this->_get(self::PRICE);
+    }
+
+    /**
+     * @return int|null
+     */
+    public function getStatus()
+    {
+        return $this->_get(self::STATUS);
+    }
+
+    /**
+     * @return int|null
+     */
+    public function getVisibility()
+    {
+        return $this->_get(self::VISIBILITY);
+    }
+
+    /**
+     * @return string|null
+     */
+    public function getTypeId()
+    {
+        return $this->_get(self::TYPE_ID);
+    }
+
+    /**
+     * @return string|null
+     */
+    public function getCreatedAt()
+    {
+        return $this->_get(self::CREATED_AT);
+    }
+
+    /**
+     * @return string|null
+     */
+    public function getUpdatedAt()
+    {
+        return $this->_get(self::UPDATED_AT);
+    }
+
+    /**
+     * @return float|null
+     */
+    public function getWeight()
+    {
+        return $this->_get(self::WEIGHT);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/ProductAttributeType.php b/app/code/Magento/Catalog/Service/V1/Data/ProductAttributeType.php
new file mode 100644
index 00000000000..c4f1778b981
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/ProductAttributeType.php
@@ -0,0 +1,58 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data;
+
+/**
+ * Class ProductAttributeType
+ * @package Magento\Catalog\Service\V1\Data
+ */
+class ProductAttributeType extends \Magento\Framework\Service\Data\AbstractObject
+{
+    /**
+     * Constants used as keys into $_data
+     */
+    const LABEL = 'label';
+
+    const VALUE = 'value';
+
+    /**
+     * Get option label
+     *
+     * @return string
+     */
+    public function getLabel()
+    {
+        return $this->_get(self::LABEL);
+    }
+
+    /**
+     * Get option value
+     *
+     * @return string
+     */
+    public function getValue()
+    {
+        return $this->_get(self::VALUE);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/ProductAttributeTypeBuilder.php b/app/code/Magento/Catalog/Service/V1/Data/ProductAttributeTypeBuilder.php
new file mode 100644
index 00000000000..570e9a581d5
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/ProductAttributeTypeBuilder.php
@@ -0,0 +1,53 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data;
+
+/**
+ * Class ProductAttributeTypeBuilder
+ * @package Magento\Catalog\Service\V1\Data\Eav
+ */
+class ProductAttributeTypeBuilder extends \Magento\Framework\Service\Data\AbstractObjectBuilder
+{
+    /**
+     * Set option label
+     *
+     * @param  string $label
+     * @return $this
+     */
+    public function setLabel($label)
+    {
+        return $this->_set(ProductAttributeType::LABEL, $label);
+    }
+
+    /**
+     * Set option value
+     *
+     * @param  string $value
+     * @return $this
+     */
+    public function setValue($value)
+    {
+        return $this->_set(ProductAttributeType::VALUE, $value);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/ProductBuilder.php b/app/code/Magento/Catalog/Service/V1/Data/ProductBuilder.php
new file mode 100644
index 00000000000..0fdda2f1eea
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/ProductBuilder.php
@@ -0,0 +1,207 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data;
+
+use Magento\Catalog\Service\V1\ProductMetadataServiceInterface;
+use Magento\Framework\Service\Data\Eav\AttributeValueBuilder;
+
+class ProductBuilder extends \Magento\Framework\Service\Data\Eav\AbstractObjectBuilder
+{
+    /**
+     * @var ProductMetadataServiceInterface
+     */
+    protected $metadataService;
+
+    /**
+     * Initialize dependencies.
+     *
+     * @param \Magento\Framework\Service\Data\ObjectFactory $objectFactory
+     * @param AttributeValueBuilder $valueBuilder
+     * @param ProductMetadataServiceInterface $metadataService
+     */
+    public function __construct(
+        \Magento\Framework\Service\Data\ObjectFactory $objectFactory,
+        AttributeValueBuilder $valueBuilder,
+        ProductMetadataServiceInterface $metadataService
+    ) {
+        parent::__construct($objectFactory, $valueBuilder);
+        $this->metadataService = $metadataService;
+    }
+
+    /**
+     * Template method used to configure the attribute codes for the product attributes
+     *
+     * @return string[]
+     */
+    public function getCustomAttributesCodes()
+    {
+        $attributeCodes = array();
+        foreach ($this->metadataService->getCustomAttributesMetadata() as $attribute) {
+            $attributeCodes[] = $attribute->getAttributeCode();
+        }
+        return $attributeCodes;
+    }
+
+    /**
+     * Set id
+     *
+     * @param int|null $value
+     * @return $this
+     */
+    public function setId($value)
+    {
+        return $this->_set(Product::ID, $value);
+    }
+
+    /**
+     * Set Sku
+     *
+     * @param string|null $value
+     * @return $this
+     */
+    public function setSku($value)
+    {
+        return $this->_set(Product::SKU, $value);
+    }
+
+    /**
+     * Set Name
+     *
+     * @param string|null $value
+     * @return $this
+     */
+    public function setName($value)
+    {
+        return $this->_set(Product::NAME, $value);
+    }
+
+    /**
+     * Set store id
+     *
+     * @param int|null $value
+     * @return $this
+     */
+    public function setStoreId($value)
+    {
+        return $this->_set(Product::STORE_ID, $value);
+    }
+
+    /**
+     * Set price
+     *
+     * @param float|null $value
+     * @return $this
+     */
+    public function setPrice($value)
+    {
+        return $this->_set(Product::PRICE, $value);
+    }
+
+    /**
+     * Set visibility
+     *
+     * @param int|null $value
+     * @return $this
+     */
+    public function setVisibility($value)
+    {
+        return $this->_set(Product::VISIBILITY, $value);
+    }
+
+    /**
+     * Set TypeId
+     *
+     * @param int|null $value
+     * @return $this
+     */
+    public function setTypeId($value)
+    {
+        return $this->_set(Product::TYPE_ID, $value);
+    }
+
+    /**
+     * Set created time
+     *
+     * @SuppressWarnings(PHPMD.UnusedFormalParameter)
+     *
+     * @param string|null $value
+     * @return $this
+     */
+    public function setCreatedAt($value)
+    {
+        throw new \Magento\Framework\Exception\InputException(
+            'Field "created_at" is readonly',
+            ['fieldName' => 'created_at']
+        );
+    }
+
+    /**
+     * Set updated time
+     *
+     * @SuppressWarnings(PHPMD.UnusedFormalParameter)
+     *
+     * @param string|null $value
+     * @return $this
+     */
+    public function setUpdatedAt($value)
+    {
+        throw new \Magento\Framework\Exception\InputException(
+            'Field "updated_at" is readonly',
+            ['fieldName' => 'updated_at']
+        );
+    }
+
+    /**
+     * Set status
+     *
+     * @param int|null $value
+     * @return $this
+     */
+    public function setAttributeSetId($value)
+    {
+        return $this->_set(Product::ATTRIBUTE_SET_ID, $value);
+    }
+
+    /**
+     * Set status
+     *
+     * @param int|null $value
+     * @return $this
+     */
+    public function setStatus($value)
+    {
+        return $this->_set(Product::STATUS, $value);
+    }
+
+    /**
+     * Set weight
+     *
+     * @param float|null $value
+     * @return $this
+     */
+    public function setWeight($value)
+    {
+        return $this->_set(Product::WEIGHT, $value);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/ProductMapper.php b/app/code/Magento/Catalog/Service/V1/Data/ProductMapper.php
new file mode 100644
index 00000000000..c3f71253c3c
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/ProductMapper.php
@@ -0,0 +1,71 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data;
+
+use \Magento\Framework\Service\EavDataObjectConverter;
+
+class ProductMapper
+{
+    /** @var  \Magento\Catalog\Model\ProductFactory */
+    protected $productFactory;
+
+    /** @var  \Magento\Catalog\Model\Product\Type */
+    protected $productTypes;
+
+    /**
+     * @param \Magento\Catalog\Model\ProductFactory $productFactory
+     * @param \Magento\Catalog\Model\Product\Type $productTypes
+     */
+    public function __construct(
+        \Magento\Catalog\Model\ProductFactory $productFactory,
+        \Magento\Catalog\Model\Product\Type $productTypes
+    ) {
+        $this->productFactory = $productFactory;
+        $this->productTypes = $productTypes;
+    }
+
+    /**
+     * @param  Product $product
+     * @param  \Magento\Catalog\Model\Product $productModel
+     * @return \Magento\Catalog\Model\Product
+     * @throws \RuntimeException
+     */
+    public function toModel(
+        Product $product,
+        \Magento\Catalog\Model\Product $productModel = null
+    ) {
+        /** @var \Magento\Catalog\Model\Product $productModel */
+        $productModel = $productModel ?: $this->productFactory->create();
+        $productModel->addData(EavDataObjectConverter::toFlatArray($product));
+        if (!is_numeric($productModel->getAttributeSetId())) {
+            $productModel->setAttributeSetId($productModel->getDefaultAttributeSetId());
+        }
+        if (!$productModel->hasTypeId()) {
+            $productModel->setTypeId(\Magento\Catalog\Model\Product\Type::DEFAULT_TYPE);
+        } else if (!isset($this->productTypes->getTypes()[$productModel->getTypeId()])) {
+            throw new \RuntimeException('Illegal product type');
+        }
+        return $productModel;
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/SearchResults.php b/app/code/Magento/Catalog/Service/V1/Data/SearchResults.php
new file mode 100644
index 00000000000..0f873ceda7a
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/SearchResults.php
@@ -0,0 +1,61 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Service\V1\Data;
+
+/**
+ * SearchResults Service Data Object used for the search service requests
+ */
+class SearchResults extends \Magento\Framework\Service\Data\AbstractObject
+{
+    /**
+     * Get items
+     *
+     * @return \Magento\Catalog\Service\V1\Data\Product[]
+     */
+    public function getItems()
+    {
+        return is_null($this->_get('items')) ? array() : $this->_get('items');
+    }
+
+    /**
+     * Get search criteria
+     *
+     * @return \Magento\Framework\Service\V1\Data\SearchCriteria
+     */
+    public function getSearchCriteria()
+    {
+        return $this->_get('search_criteria');
+    }
+
+    /**
+     * Get total count
+     *
+     * @return int
+     */
+    public function getTotalCount()
+    {
+        return $this->_get('total_count');
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Data/SearchResultsBuilder.php b/app/code/Magento/Catalog/Service/V1/Data/SearchResultsBuilder.php
new file mode 100644
index 00000000000..9335515de92
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/Data/SearchResultsBuilder.php
@@ -0,0 +1,68 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Service\V1\Data;
+
+use Magento\Framework\Service\V1\Data\SearchCriteria;
+
+/**
+ * Builder for the SearchResults Service Data Object
+ *
+ * @method SearchResults create()
+ */
+class SearchResultsBuilder extends \Magento\Framework\Service\Data\AbstractObjectBuilder
+{
+    /**
+     * Set search criteria
+     *
+     * @param SearchCriteria $searchCriteria
+     * @return $this
+     */
+    public function setSearchCriteria(SearchCriteria $searchCriteria)
+    {
+        return $this->_set('search_criteria', $searchCriteria);
+    }
+
+    /**
+     * Set total count
+     *
+     * @param int $totalCount
+     * @return $this
+     */
+    public function setTotalCount($totalCount)
+    {
+        return $this->_set('total_count', $totalCount);
+    }
+
+    /**
+     * Set items
+     *
+     * @param \Magento\Catalog\Service\V1\Data\Product[] $items
+     * @return $this
+     */
+    public function setItems($items)
+    {
+        return $this->_set('items', $items);
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/Product/Link/ReadService.php b/app/code/Magento/Catalog/Service/V1/Product/Link/ReadService.php
index 5e2a652a8e6..b4b28375521 100644
--- a/app/code/Magento/Catalog/Service/V1/Product/Link/ReadService.php
+++ b/app/code/Magento/Catalog/Service/V1/Product/Link/ReadService.php
@@ -28,6 +28,7 @@ use \Magento\Catalog\Model\Product\LinkTypeProvider;
 use \Magento\Catalog\Service\V1\Product\Link\Data\LinkType;
 use \Magento\Catalog\Service\V1\Product\Link\Data\ProductLink;
 use \Magento\Framework\Logger;
+use Magento\Catalog\Service\V1\Product\ProductLoader;
 
 /**
  * Class ReadService
diff --git a/app/code/Magento/Catalog/Service/V1/Product/Link/WriteService.php b/app/code/Magento/Catalog/Service/V1/Product/Link/WriteService.php
index dfc04fb088f..686e986983f 100644
--- a/app/code/Magento/Catalog/Service/V1/Product/Link/WriteService.php
+++ b/app/code/Magento/Catalog/Service/V1/Product/Link/WriteService.php
@@ -30,6 +30,7 @@ use \Magento\Catalog\Service\V1\Product\Link\Data\ProductLink;
 use \Magento\Framework\Exception\NoSuchEntityException;
 use \Magento\Catalog\Model\Resource\Product as ProductResource;
 use \Magento\Catalog\Service\V1\Product\Link\Data\ProductLink\ProductEntity\ConverterPool;
+use Magento\Catalog\Service\V1\Product\ProductLoader;
 
 class WriteService implements WriteServiceInterface
 {
diff --git a/app/code/Magento/Catalog/Service/V1/Product/Link/ProductLoader.php b/app/code/Magento/Catalog/Service/V1/Product/ProductLoader.php
similarity index 86%
rename from app/code/Magento/Catalog/Service/V1/Product/Link/ProductLoader.php
rename to app/code/Magento/Catalog/Service/V1/Product/ProductLoader.php
index 8ebbe959f1c..2345cc904a4 100644
--- a/app/code/Magento/Catalog/Service/V1/Product/Link/ProductLoader.php
+++ b/app/code/Magento/Catalog/Service/V1/Product/ProductLoader.php
@@ -18,11 +18,10 @@
  * versions in the future. If you wish to customize Magento for your
  * needs please refer to http://www.magentocommerce.com for more information.
  *
- * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
- * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ * @copyright Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
-
-namespace Magento\Catalog\Service\V1\Product\Link;
+namespace Magento\Catalog\Service\V1\Product;
 
 use \Magento\Framework\Exception\NoSuchEntityException;
 
@@ -44,7 +43,7 @@ class ProductLoader
     /**
      * Load product by SKU
      *
-     * @param string $productSku
+     * @param  string $productSku
      * @return \Magento\Catalog\Model\Product
      * @throws NoSuchEntityException
      */
diff --git a/app/code/Magento/Catalog/Service/V1/ProductAttributeReadService.php b/app/code/Magento/Catalog/Service/V1/ProductAttributeReadService.php
new file mode 100644
index 00000000000..27fd89b3490
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/ProductAttributeReadService.php
@@ -0,0 +1,88 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1;
+
+use Magento\Catalog\Model\Product\Attribute\Source\InputtypeFactory;
+
+/**
+ * Class ProductAttributeReadService
+ * @package Magento\Catalog\Service\V1
+ */
+class ProductAttributeReadService implements ProductAttributeReadServiceInterface
+{
+    /**
+     * @var ProductMetadataServiceInterface
+     */
+    private $metadataService;
+
+    /**
+     * @var \Magento\Catalog\Model\Product\Attribute\Source\InputtypeFactory
+     */
+    private $inputTypeFactory;
+
+    /**
+     * @var Data\ProductAttributeTypeBuilder
+     */
+    private $attributeTypeBuilder;
+
+    /**
+     * @param ProductMetadataServiceInterface $metadataService
+     * @param InputtypeFactory $inputTypeFactory
+     * @param Data\ProductAttributeTypeBuilder $attributeTypeBuilder
+     */
+    public function __construct(
+        ProductMetadataServiceInterface $metadataService,
+        InputtypeFactory $inputTypeFactory,
+        Data\ProductAttributeTypeBuilder $attributeTypeBuilder
+    ) {
+        $this->metadataService = $metadataService;
+        $this->inputTypeFactory = $inputTypeFactory;
+        $this->attributeTypeBuilder = $attributeTypeBuilder;
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function types()
+    {
+        $types = [];
+        $inputType = $this->inputTypeFactory->create();
+
+        foreach ($inputType->toOptionArray() as $option) {
+            $types[] = $this->attributeTypeBuilder->populateWithArray($option)->create();
+        }
+        return $types;
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function info($id)
+    {
+        return $this->metadataService->getAttributeMetadata(
+            ProductMetadataServiceInterface::ENTITY_TYPE_PRODUCT,
+            $id
+        );
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/ProductAttributeReadServiceInterface.php b/app/code/Magento/Catalog/Service/V1/ProductAttributeReadServiceInterface.php
new file mode 100644
index 00000000000..7a1717db1cf
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/ProductAttributeReadServiceInterface.php
@@ -0,0 +1,50 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1;
+
+use Magento\Catalog\Service\V1\Data\ProductAttributeType;
+
+/**
+ * Class ProductAttributeReadServiceInterface
+ * @package Magento\Catalog\Service\V1
+ */
+interface ProductAttributeReadServiceInterface
+{
+    /**
+     * Retrieve list of product attribute types
+     *
+     * @return \Magento\Catalog\Service\V1\Data\ProductAttributeType[]
+     */
+    public function types();
+
+    /**
+     * Get full information about a required attribute with the list of options
+     *
+     * @param  string $id
+     * @return \Magento\Catalog\Service\V1\Data\Eav\AttributeMetadata
+     *
+     * @throws \Magento\Framework\Exception\NoSuchEntityException
+     */
+    public function info($id);
+}
diff --git a/app/code/Magento/Catalog/Service/V1/ProductMetadataService.php b/app/code/Magento/Catalog/Service/V1/ProductMetadataService.php
new file mode 100644
index 00000000000..979a89caeec
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/ProductMetadataService.php
@@ -0,0 +1,201 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1;
+
+use Magento\Eav\Model\Entity\Attribute\AbstractAttribute;
+use Magento\Framework\Exception\NoSuchEntityException;
+use Magento\Catalog\Service\V1\Data\Eav\AttributeMetadata;
+
+/**
+ * Class ProductMetadataService
+ * @package Magento\Catalog\Service\V1
+ */
+class ProductMetadataService implements ProductMetadataServiceInterface
+{
+    /**
+     * @var \Magento\Eav\Model\Config
+     */
+    private $eavConfig;
+
+    /**
+     * @var \Magento\Framework\App\ScopeResolverInterface
+     */
+    private $scopeResolver;
+
+    /**
+     * @var Data\Eav\OptionBuilder
+     */
+    private $optionBuilder;
+
+    /**
+     * @var Data\Eav\ValidationRuleBuilder
+     */
+    private $validationRuleBuilder;
+
+    /**
+     * @var Data\Eav\AttributeMetadataBuilder
+     */
+    private $attributeMetadataBuilder;
+
+    /**
+     * @param \Magento\Eav\Model\Config $eavConfig
+     * @param \Magento\Framework\App\ScopeResolverInterface $scopeResolver
+     * @param Data\Eav\OptionBuilder $optionBuilder
+     * @param Data\Eav\ValidationRuleBuilder $validationRuleBuilder
+     * @param Data\Eav\AttributeMetadataBuilder $attributeMetadataBuilder
+     */
+    public function __construct(
+        \Magento\Eav\Model\Config $eavConfig,
+        \Magento\Framework\App\ScopeResolverInterface $scopeResolver,
+        Data\Eav\OptionBuilder $optionBuilder,
+        Data\Eav\ValidationRuleBuilder $validationRuleBuilder,
+        Data\Eav\AttributeMetadataBuilder $attributeMetadataBuilder
+    ) {
+        $this->eavConfig = $eavConfig;
+        $this->scopeResolver = $scopeResolver;
+        $this->optionBuilder = $optionBuilder;
+        $this->validationRuleBuilder = $validationRuleBuilder;
+        $this->attributeMetadataBuilder = $attributeMetadataBuilder;
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function getCustomAttributesMetadata()
+    {
+        $customAttributes = [];
+        foreach ($this->getProductAttributesMetadata() as $attributeMetadata) {
+            $customAttributes[] = $attributeMetadata;
+        }
+        return $customAttributes;
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function getProductAttributesMetadata()
+    {
+        return $this->getAllAttributeSetMetadata(self::ENTITY_TYPE_PRODUCT, self::ATTRIBUTE_SET_ID_PRODUCT);
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function getAllAttributeSetMetadata($entityType, $attributeSetId = 0, $scopeCode = null)
+    {
+        if (null === $scopeCode) {
+            $scopeCode = $this->scopeResolver->getScope()->getCode();
+        }
+        $object = new \Magento\Framework\Object(
+            [
+                'store_id' => $scopeCode,
+                'attribute_set_id' => $attributeSetId,
+            ]
+        );
+        $attributeCodes = $this->eavConfig->getEntityAttributeCodes($entityType, $object);
+
+        $attributesMetadata = [];
+        foreach ($attributeCodes as $attributeCode) {
+            try {
+                $attributesMetadata[] = $this->getAttributeMetadata($entityType, $attributeCode);
+            } catch (NoSuchEntityException $e) {
+                //If no such entity, skip
+            }
+        }
+        return $attributesMetadata;
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function getAttributeMetadata($entityType, $attributeCode)
+    {
+        /** @var AbstractAttribute $attribute */
+        $attribute = $this->eavConfig->getAttribute($entityType, $attributeCode);
+        if ($attribute) {
+            $attributeMetadata = $this->createMetadataAttribute($attribute);
+            return $attributeMetadata;
+        } else {
+            throw (new NoSuchEntityException('entityType', array($entityType)))
+                ->singleField('attributeCode', $attributeCode);
+        }
+    }
+
+    /**
+     * @param  AbstractAttribute $attribute
+     * @return Data\Eav\AttributeMetadata
+     */
+    private function createMetadataAttribute($attribute)
+    {
+        $data = $this->booleanPrefixMapper($attribute->getData());
+
+        // fill options and validate rules
+        $data[AttributeMetadata::OPTIONS] = $attribute->usesSource()
+            ? $attribute->getSource()->getAllOptions() : array();
+        $data[AttributeMetadata::VALIDATION_RULES] = $attribute->getValidateRules();
+
+        // fill scope
+        $data[AttributeMetadata::SCOPE] = $attribute->isScopeGlobal()
+            ? 'global' : ($attribute->isScopeWebsite() ? 'website' : 'store');
+
+        // fill frontend labels
+        $data[AttributeMetadata::FRONTEND_LABEL] = array(
+            array(
+                'store_id' => 0,
+                'label' => $attribute->getFrontendLabel()
+            )
+        );
+        if (is_array($attribute->getStoreLabels())) {
+            foreach ($attribute->getStoreLabels() as $storeId => $label) {
+                $data[AttributeMetadata::FRONTEND_LABEL][] = array(
+                    'store_id' => $storeId,
+                    'label' => $label
+                );
+            }
+        }
+        return $this->attributeMetadataBuilder->populateWithArray($data)->create();
+    }
+
+    /**
+     * Remove 'is_' prefixes for Attribute fields to make DTO interface more natural
+     *
+     * @param array $attributeFields
+     * @return array
+     */
+    private function booleanPrefixMapper(array $attributeFields)
+    {
+        $prefix = 'is_';
+        foreach ($attributeFields as $key => $value) {
+            if (strpos($key, $prefix) !== 0) {
+                continue;
+            }
+            $postfix = substr($key, strlen($prefix));
+            if (!isset($attributeFields[$postfix])) {
+                $attributeFields[$postfix] = $value;
+                unset($attributeFields[$key]);
+            }
+        }
+        return $attributeFields;
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/ProductMetadataServiceInterface.php b/app/code/Magento/Catalog/Service/V1/ProductMetadataServiceInterface.php
new file mode 100644
index 00000000000..aabe06dd027
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/ProductMetadataServiceInterface.php
@@ -0,0 +1,73 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1;
+
+/**
+ * Class ProductMetadataServiceInterface
+ * @package Magento\Catalog\Service\V1
+ */
+interface ProductMetadataServiceInterface
+{
+    /**#@+
+     * Predefined constants
+     */
+    const ENTITY_TYPE_PRODUCT           = 'catalog_product';
+
+    const ATTRIBUTE_SET_ID_PRODUCT      = 4;
+    /**#@-*/
+
+    /**
+     * Retrieve custom EAV attribute metadata of product
+     *
+     * @return array<Data\Eav\AttributeMetadata>
+     */
+    public function getCustomAttributesMetadata();
+
+    /**
+     * Retrieve EAV attribute metadata of product
+     *
+     * @return Data\Eav\AttributeMetadata[]
+     */
+    public function getProductAttributesMetadata();
+
+    /**
+     * Returns all known attributes metadata for a given entity type
+     *
+     * @param  string $entityType
+     * @param  int $attributeSetId
+     * @param  int $storeId
+     * @return Data\Eav\AttributeMetadata[]
+     */
+    public function getAllAttributeSetMetadata($entityType, $attributeSetId = 0, $storeId = null);
+
+    /**
+     * Retrieve Attribute Metadata
+     *
+     * @param  string $entityType
+     * @param  string $attributeCode
+     * @return Data\Eav\AttributeMetadata
+     * @throws \Magento\Framework\Exception\NoSuchEntityException
+     */
+    public function getAttributeMetadata($entityType, $attributeCode);
+}
diff --git a/app/code/Magento/Catalog/Service/V1/ProductService.php b/app/code/Magento/Catalog/Service/V1/ProductService.php
new file mode 100644
index 00000000000..ff88e63a3df
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/ProductService.php
@@ -0,0 +1,269 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1;
+
+use Magento\Catalog\Controller\Adminhtml\Product;
+use Magento\Framework\Exception\NoSuchEntityException;
+use Magento\Catalog\Service\V1\Data\Converter;
+use Magento\Framework\Service\V1\Data\SearchCriteria;
+use Magento\Catalog\Service\V1\Data\Product as ProductData;
+use Magento\Framework\Service\V1\Data\Search\FilterGroup;
+use Magento\Catalog\Model\Resource\Product\Collection;
+
+/**
+ * Class ProductService
+ * @package Magento\Catalog\Service\V1
+ * @SuppressWarnings(PHPMD.CouplingBetweenObjects)
+ */
+class ProductService implements ProductServiceInterface
+{
+    /**
+     * @var Product\Initialization\Helper
+     */
+    private $initializationHelper;
+
+    /**
+     * @var \Magento\Catalog\Service\V1\Data\ProductMapper
+     */
+    protected $productMapper;
+
+    /**
+     * @var \Magento\Catalog\Model\Product\TypeTransitionManager
+     */
+    private $productTypeManager;
+
+    /**
+     * @var \Magento\Catalog\Service\V1\Product\ProductLoader
+     */
+    private $productLoader;
+
+    /**
+     * @var \Magento\Catalog\Model\Resource\Product\CollectionFactory
+     */
+    private $productCollection;
+
+    /**
+     * @var ProductMetadataServiceInterface
+     */
+    private $metadataService;
+
+    /**
+     * @var Converter
+     */
+    private $converter;
+
+    /**
+     * @var Data\SearchResultsBuilder
+     */
+    private $searchResultsBuilder;
+
+    /**
+     * @param Product\Initialization\Helper $initializationHelper
+     * @param Data\ProductMapper $productMapper
+     * @param \Magento\Catalog\Model\Product\TypeTransitionManager $productTypeManager
+     * @param \Magento\Catalog\Service\V1\Product\ProductLoader $productLoader
+     * @param \Magento\Catalog\Model\Resource\Product\CollectionFactory $productCollection
+     * @param ProductMetadataServiceInterface $metadataService
+     * @param \Magento\Catalog\Service\V1\Data\Converter $converter
+     * @param Data\SearchResultsBuilder $searchResultsBuilder
+     */
+    public function __construct(
+        Product\Initialization\Helper $initializationHelper,
+        \Magento\Catalog\Service\V1\Data\ProductMapper $productMapper,
+        \Magento\Catalog\Model\Product\TypeTransitionManager $productTypeManager,
+        \Magento\Catalog\Service\V1\Product\ProductLoader $productLoader,
+        \Magento\Catalog\Model\Resource\Product\CollectionFactory $productCollection,
+        ProductMetadataServiceInterface $metadataService,
+        \Magento\Catalog\Service\V1\Data\Converter $converter,
+        Data\SearchResultsBuilder $searchResultsBuilder
+    ) {
+        $this->initializationHelper = $initializationHelper;
+        $this->productMapper = $productMapper;
+        $this->productTypeManager = $productTypeManager;
+        $this->productLoader = $productLoader;
+        $this->productCollection = $productCollection;
+        $this->metadataService = $metadataService;
+        $this->converter = $converter;
+        $this->searchResultsBuilder = $searchResultsBuilder;
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function create(\Magento\Catalog\Service\V1\Data\Product $product)
+    {
+        try {
+            $productModel = $this->productMapper->toModel($product);
+            $this->initializationHelper->initialize($productModel);
+            $productModel->validate();
+            $productModel->save();
+        } catch (\Magento\Eav\Model\Entity\Attribute\Exception $exception) {
+            throw \Magento\Framework\Exception\InputException::invalidFieldValue(
+                $exception->getAttributeCode(),
+                $productModel->getData($exception->getAttributeCode()),
+                $exception
+            );
+        }
+        if (!$productModel->getId()) {
+            throw new \Magento\Framework\Exception\StateException('Unable to save product');
+        }
+        return $productModel->getSku();
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function update($id, \Magento\Catalog\Service\V1\Data\Product $product)
+    {
+        $productModel = $this->productLoader->load($id);
+        try {
+            $this->productMapper->toModel($product, $productModel);
+            $this->initializationHelper->initialize($productModel);
+            $this->productTypeManager->processProduct($productModel);
+            $productModel->validate();
+            $productModel->save();
+        } catch (\Magento\Eav\Model\Entity\Attribute\Exception $exception) {
+            throw \Magento\Framework\Exception\InputException::invalidFieldValue(
+                $exception->getAttributeCode(),
+                $productModel->getData($exception->getAttributeCode()),
+                $exception
+            );
+        }
+        return $productModel->getSku();
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function delete($id)
+    {
+        $product = $this->productLoader->load($id);
+        $product->delete();
+        return true;
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function get($id)
+    {
+        return $this->converter->createProductDataFromModel($this->productLoader->load($id));
+    }
+
+    /**
+     * {@inheritdoc}
+     * Example of request:
+     * {
+     *     "searchCriteria": {
+     *         "filterGroups": [
+     *             {
+     *                 "filters": [
+     *                     {"value": "16.000", "conditionType" : "eq", "field" : "price"}
+     *                 ]
+     *             }
+     *         ]
+     *     },
+     *     "sort_orders" : {"id": "1"},
+     *     "page_size" : "30",
+     *     "current_page" : "10"
+     * }
+     *
+     * products?searchCriteria[filterGroups][0][filters][0][field]=price&
+     * searchCriteria[filterGroups][0][filters][0][value]=16.000&page_size=30&current_page=1&sort_orders[id]=1
+     */
+    public function search(SearchCriteria $searchCriteria)
+    {
+        $this->searchResultsBuilder->setSearchCriteria($searchCriteria);
+        /** @var \Magento\Catalog\Model\Resource\Product\Collection $collection */
+        $collection = $this->productCollection->create();
+        // This is needed to make sure all the attributes are properly loaded
+        foreach ($this->metadataService->getProductAttributesMetadata() as $metadata) {
+            $collection->addAttributeToSelect($metadata->getAttributeCode());
+        }
+
+        $collection->joinAttribute('status', 'catalog_product/status', 'entity_id', null, 'inner');
+        $collection->joinAttribute('visibility', 'catalog_product/visibility', 'entity_id', null, 'inner');
+
+        //Add filters from root filter group to the collection
+        foreach ($searchCriteria->getFilterGroups() as $group) {
+            $this->addFilterGroupToCollection($group, $collection);
+        }
+        $sortOrders = $searchCriteria->getSortOrders();
+        if ($sortOrders) {
+            foreach ($searchCriteria->getSortOrders() as $field => $direction) {
+                $field = $this->translateField($field);
+                $collection->addOrder($field, $direction == SearchCriteria::SORT_ASC ? 'ASC' : 'DESC');
+            }
+        }
+        $collection->setCurPage($searchCriteria->getCurrentPage());
+        $collection->setPageSize($searchCriteria->getPageSize());
+        $this->searchResultsBuilder->setTotalCount($collection->getSize());
+
+        $products = array();
+        /** @var \Magento\Catalog\Model\Product $productModel */
+        foreach ($collection as $productModel) {
+            $products[] = $this->converter->createProductDataFromModel($productModel);
+        }
+
+        $this->searchResultsBuilder->setItems($products);
+        return $this->searchResultsBuilder->create();
+    }
+
+    /**
+     * Helper function that adds a FilterGroup to the collection.
+     *
+     * @param FilterGroup $filterGroup
+     * @param Collection $collection
+     * @return void
+     * @throws \Magento\Framework\Exception\InputException
+     */
+    protected function addFilterGroupToCollection(FilterGroup $filterGroup, Collection $collection)
+    {
+        $fields = [];
+        foreach ($filterGroup->getFilters() as $filter) {
+            $condition = $filter->getConditionType() ? $filter->getConditionType() : 'eq';
+            $field = $this->translateField($filter->getField());
+            $fields[] = array('attribute' => $field, $condition => $filter->getValue());
+        }
+        if ($fields) {
+            $collection->addFieldToFilter($fields);
+        }
+    }
+
+    /**
+     * Translates a field name to a DB column name for use in collection queries.
+     *
+     * @param string $field a field name that should be translated to a DB column name.
+     * @return string
+     */
+    protected function translateField($field)
+    {
+        switch ($field) {
+            case ProductData::ID:
+                return 'entity_id';
+            default:
+                return $field;
+        }
+    }
+}
diff --git a/app/code/Magento/Catalog/Service/V1/ProductServiceInterface.php b/app/code/Magento/Catalog/Service/V1/ProductServiceInterface.php
new file mode 100644
index 00000000000..02d4ca463a4
--- /dev/null
+++ b/app/code/Magento/Catalog/Service/V1/ProductServiceInterface.php
@@ -0,0 +1,81 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1;
+
+/**
+ * Class ProductServiceInterface
+ * @package Magento\Catalog\Service\V1
+ */
+interface ProductServiceInterface
+{
+    /**
+     * Get product info
+     *
+     * @param  string $id
+     * @throws \Magento\Framework\Exception\NoSuchEntityException If ID is not found
+     * @return \Magento\Catalog\Service\V1\Data\Product $product
+     */
+    public function get($id);
+
+    /**
+     * Delete product
+     *
+     * @param  string $id
+     * @throws \Magento\Framework\Exception\NoSuchEntityException If ID is not found
+     * @throws \Exception If something goes wrong during delete
+     * @return bool True if the entity was deleted (always true)
+     */
+    public function delete($id);
+
+    /**
+     * Save product process
+     *
+     * @param  \Magento\Catalog\Service\V1\Data\Product $product
+     * @throws \Magento\Framework\Exception\InputException If there is a problem with the input
+     * @throws \Magento\Framework\Exception\NoSuchEntityException If a ID is sent but the entity does not exist
+     * @throws \Magento\Framework\Model\Exception If something goes wrong during save
+     * @return string id
+     */
+    public function create(\Magento\Catalog\Service\V1\Data\Product $product);
+
+    /**
+     * Update product process
+     *
+     * @param  string $id
+     * @param  \Magento\Catalog\Service\V1\Data\Product $product
+     * @throws \Magento\Framework\Exception\InputException If there is a problem with the input
+     * @throws \Magento\Framework\Exception\NoSuchEntityException If a ID is sent but the entity does not exist
+     * @throws \Magento\Framework\Model\Exception If something goes wrong during save
+     * @return string id
+     */
+    public function update($id, \Magento\Catalog\Service\V1\Data\Product $product);
+
+    /**
+     * get product list product
+     *
+     * @param \Magento\Framework\Service\V1\Data\SearchCriteria $searchCriteria
+     * @return \Magento\Catalog\Service\V1\Data\SearchResults containing Data\Product objects
+     */
+    public function search(\Magento\Framework\Service\V1\Data\SearchCriteria $searchCriteria);
+}
diff --git a/app/code/Magento/Catalog/etc/di.xml b/app/code/Magento/Catalog/etc/di.xml
index 36f1c3c6522..37365f8cb65 100644
--- a/app/code/Magento/Catalog/etc/di.xml
+++ b/app/code/Magento/Catalog/etc/di.xml
@@ -24,6 +24,9 @@
  */
 -->
 <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/ObjectManager/etc/config.xsd">
+    <preference for="Magento\Catalog\Service\V1\ProductMetadataServiceInterface" type="Magento\Catalog\Service\V1\ProductMetadataService" />
+    <preference for="Magento\Catalog\Service\V1\ProductServiceInterface" type="Magento\Catalog\Service\V1\ProductService" />
+    <preference for="Magento\Catalog\Service\V1\ProductAttributeReadServiceInterface" type="Magento\Catalog\Service\V1\ProductAttributeReadService" />
     <preference for="Magento\Catalog\Model\ProductTypes\ConfigInterface" type="Magento\Catalog\Model\ProductTypes\Config" />
     <preference for="Magento\Catalog\Model\ProductOptions\ConfigInterface" type="Magento\Catalog\Model\ProductOptions\Config" />
     <preference for="Magento\Catalog\Model\Product\PriceModifierInterface" type="Magento\Catalog\Model\Product\PriceModifier\Composite" />
diff --git a/app/code/Magento/Catalog/etc/webapi.xml b/app/code/Magento/Catalog/etc/webapi.xml
index 480a7f47bf1..cd647e5e9e7 100644
--- a/app/code/Magento/Catalog/etc/webapi.xml
+++ b/app/code/Magento/Catalog/etc/webapi.xml
@@ -25,6 +25,48 @@
 -->
 <routes xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:noNamespaceSchemaLocation="../../../../../app/code/Magento/Webapi/etc/webapi.xsd">
+    <route url="/V1/products" method="POST">
+        <service class="Magento\Catalog\Service\V1\ProductServiceInterface" method="create"/>
+        <resources>
+            <resource ref="Magento_Catalog::products" />
+        </resources>
+    </route>
+    <route url="/V1/products/:id" method="PUT">
+        <service class="Magento\Catalog\Service\V1\ProductServiceInterface" method="update" />
+        <resources>
+            <resource ref="Magento_Catalog::products" />
+        </resources>
+    </route>
+    <route url="/V1/products/:id" method="DELETE">
+        <service class="Magento\Catalog\Service\V1\ProductServiceInterface" method="delete"/>
+        <resources>
+            <resource ref="Magento_Catalog::products" />
+        </resources>
+    </route>
+    <route url="/V1/products" method="GET">
+        <service class="Magento\Catalog\Service\V1\ProductServiceInterface" method="search"/>
+        <resources>
+            <resource ref="Magento_Catalog::products" />
+        </resources>
+    </route>
+    <route url="/V1/products/:id" method="GET">
+        <service class="Magento\Catalog\Service\V1\ProductServiceInterface" method="get"/>
+        <resources>
+            <resource ref="Magento_Catalog::products" />
+        </resources>
+    </route>
+    <route url="/V1/products/attributes/types" method="GET">
+        <service class="Magento\Catalog\Service\V1\ProductAttributeReadServiceInterface" method="types"/>
+        <resources>
+            <resource ref="Magento_Catalog::attributes_attributes" />
+        </resources>
+    </route>
+    <route url="/V1/products/attributes/:id" method="GET">
+        <service class="Magento\Catalog\Service\V1\ProductAttributeReadServiceInterface" method="info"/>
+        <resources>
+            <resource ref="Magento_Catalog::attributes_attributes" />
+        </resources>
+    </route>
     <route url="/V1/products/types" method="GET">
         <service class="Magento\Catalog\Service\V1\ProductTypeServiceInterface" method="getProductTypes"/>
         <resources>
diff --git a/app/code/Magento/Catalog/sql/catalog_setup/install-1.6.0.0.0.php b/app/code/Magento/Catalog/sql/catalog_setup/install-1.6.0.0.0.php
index b4d05308e54..314021364e2 100644
--- a/app/code/Magento/Catalog/sql/catalog_setup/install-1.6.0.0.0.php
+++ b/app/code/Magento/Catalog/sql/catalog_setup/install-1.6.0.0.0.php
@@ -171,9 +171,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('catalog_product_entity_datetime', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_datetime', array('entity_id')),
-    array('entity_id')
 )->addForeignKey(
     $installer->getFkName('catalog_product_entity_datetime', 'attribute_id', 'eav_attribute', 'attribute_id'),
     'attribute_id',
@@ -252,9 +249,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('catalog_product_entity_decimal', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_decimal', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_entity_decimal', array('attribute_id')),
     array('attribute_id')
@@ -339,9 +333,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('catalog_product_entity_int', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_int', array('entity_id')),
-    array('entity_id')
 )->addForeignKey(
     $installer->getFkName('catalog_product_entity_int', 'attribute_id', 'eav_attribute', 'attribute_id'),
     'attribute_id',
@@ -423,9 +414,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('catalog_product_entity_text', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_text', array('entity_id')),
-    array('entity_id')
 )->addForeignKey(
     $installer->getFkName('catalog_product_entity_text', 'attribute_id', 'eav_attribute', 'attribute_id'),
     'attribute_id',
@@ -507,9 +495,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('catalog_product_entity_varchar', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_varchar', array('entity_id')),
-    array('entity_id')
 )->addForeignKey(
     $installer->getFkName('catalog_product_entity_varchar', 'attribute_id', 'eav_attribute', 'attribute_id'),
     'attribute_id',
@@ -1281,9 +1266,6 @@ $table = $installer->getConnection()->newTable(
     null,
     array('unsigned' => true),
     'Store ID'
-)->addIndex(
-    $installer->getIdxName('catalog_compare_item', array('customer_id')),
-    array('customer_id')
 )->addIndex(
     $installer->getIdxName('catalog_compare_item', array('product_id')),
     array('product_id')
@@ -1471,9 +1453,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('catalog_product_link', array('linked_product_id')),
     array('linked_product_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_link', array('link_type_id')),
-    array('link_type_id')
 )->addForeignKey(
     $installer->getFkName('catalog_product_link', 'linked_product_id', 'catalog_product_entity', 'entity_id'),
     'linked_product_id',
@@ -1578,9 +1557,6 @@ $table = $installer->getConnection()->newTable(
     '12,4',
     array('nullable' => false, 'default' => '0.0000'),
     'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_link_attribute_decimal', array('product_link_attribute_id')),
-    array('product_link_attribute_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_link_attribute_decimal', array('link_id')),
     array('link_id')
@@ -1645,9 +1621,6 @@ $table = $installer->getConnection()->newTable(
     null,
     array('nullable' => false, 'default' => '0'),
     'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_link_attribute_int', array('product_link_attribute_id')),
-    array('product_link_attribute_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_link_attribute_int', array('link_id')),
     array('link_id')
@@ -1712,9 +1685,6 @@ $table = $installer->getConnection()->newTable(
     255,
     array(),
     'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_link_attribute_varchar', array('product_link_attribute_id')),
-    array('product_link_attribute_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_link_attribute_varchar', array('link_id')),
     array('link_id')
@@ -1805,9 +1775,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('entity_id', 'all_groups', 'customer_group_id', 'qty', 'website_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_tier_price', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_entity_tier_price', array('customer_group_id')),
     array('customer_group_id')
@@ -2084,9 +2051,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('option_id', 'store_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_price', array('option_id')),
-    array('option_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_option_price', array('store_id')),
     array('store_id')
@@ -2146,9 +2110,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('option_id', 'store_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_title', array('option_id')),
-    array('option_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_option_title', array('store_id')),
     array('store_id')
@@ -2258,9 +2219,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('option_type_id', 'store_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_type_price', array('option_type_id')),
-    array('option_type_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_option_type_price', array('store_id')),
     array('store_id')
@@ -2325,9 +2283,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('option_type_id', 'store_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_type_title', array('option_type_id')),
-    array('option_type_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_option_type_title', array('store_id')),
     array('store_id')
@@ -2554,9 +2509,6 @@ $table = $installer->getConnection()->newTable(
     null,
     array('unsigned' => true, 'nullable' => false, 'primary' => true),
     'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_index_eav', array('attribute_id')),
     array('attribute_id')
@@ -2621,9 +2573,6 @@ $table = $installer->getConnection()->newTable(
     '12,4',
     array('nullable' => false, 'primary' => true),
     'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_index_eav_decimal', array('attribute_id')),
     array('attribute_id')
@@ -2721,9 +2670,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('catalog_product_index_price', array('customer_group_id')),
     array('customer_group_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_price', array('website_id')),
-    array('website_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_index_price', array('min_price')),
     array('min_price')
@@ -3406,9 +3352,6 @@ $table = $installer->getConnection()->newTable(
     null,
     array('unsigned' => true, 'nullable' => false, 'primary' => true),
     'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_idx', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_index_eav_idx', array('attribute_id')),
     array('attribute_id')
@@ -3452,9 +3395,6 @@ $table = $installer->getConnection()->newTable(
     null,
     array('unsigned' => true, 'nullable' => false, 'primary' => true),
     'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_tmp', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_index_eav_tmp', array('attribute_id')),
     array('attribute_id')
@@ -3498,9 +3438,6 @@ $table = $installer->getConnection()->newTable(
     '12,4',
     array('nullable' => false, 'primary' => true),
     'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal_idx', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_index_eav_decimal_idx', array('attribute_id')),
     array('attribute_id')
@@ -3544,9 +3481,6 @@ $table = $installer->getConnection()->newTable(
     '12,4',
     array('nullable' => false, 'primary' => true),
     'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal_tmp', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_index_eav_decimal_tmp', array('attribute_id')),
     array('attribute_id')
diff --git a/app/code/Magento/Catalog/sql/catalog_setup/install-1.6.0.0.php b/app/code/Magento/Catalog/sql/catalog_setup/install-1.6.0.0.php
deleted file mode 100644
index cab8c17458c..00000000000
--- a/app/code/Magento/Catalog/sql/catalog_setup/install-1.6.0.0.php
+++ /dev/null
@@ -1,3993 +0,0 @@
-<?php
-/**
- * Magento
- *
- * NOTICE OF LICENSE
- *
- * This source file is subject to the Open Software License (OSL 3.0)
- * that is bundled with this package in the file LICENSE.txt.
- * It is also available through the world-wide-web at this URL:
- * http://opensource.org/licenses/osl-3.0.php
- * If you did not receive a copy of the license and are unable to
- * obtain it through the world-wide-web, please send an email
- * to license@magentocommerce.com so we can send you a copy immediately.
- *
- * DISCLAIMER
- *
- * Do not edit or add to this file if you wish to upgrade Magento to newer
- * versions in the future. If you wish to customize Magento for your
- * needs please refer to http://www.magentocommerce.com for more information.
- *
- * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
- * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
- */
-
-$installer = $this;
-/* @var $installer \Magento\Catalog\Model\Resource\Setup */
-
-$installer->startSetup();
-
-/**
- * Create table 'catalog_product_entity'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_entity')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_set_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute Set ID'
-)->addColumn(
-    'type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    32,
-    array('nullable' => false, 'default' => \Magento\Catalog\Model\Product\Type::DEFAULT_TYPE),
-    'Type ID'
-)->addColumn(
-    'sku',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    64,
-    array(),
-    'SKU'
-)->addColumn(
-    'has_options',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('nullable' => false, 'default' => '0'),
-    'Has Options'
-)->addColumn(
-    'required_options',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Required Options'
-)->addColumn(
-    'created_at',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TIMESTAMP,
-    null,
-    array(),
-    'Creation Time'
-)->addColumn(
-    'updated_at',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TIMESTAMP,
-    null,
-    array(),
-    'Update Time'
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity', array('entity_type_id')),
-    array('entity_type_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity', array('attribute_set_id')),
-    array('attribute_set_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity', array('sku')),
-    array('sku')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity', 'attribute_set_id', 'eav_attribute_set', 'attribute_set_id'),
-    'attribute_set_id',
-    $installer->getTable('eav_attribute_set'),
-    'attribute_set_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity', 'entity_type_id', 'eav_entity_type', 'entity_type_id'),
-    'entity_type_id',
-    $installer->getTable('eav_entity_type'),
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Table'
-);
-$installer->getConnection()->createTable($table);
-
-
-
-/**
- * Create table 'catalog_product_entity_datetime'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_entity_datetime')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DATETIME,
-    null,
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_entity_datetime',
-        array('entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_datetime', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_datetime', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_datetime', array('entity_id')),
-    array('entity_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_datetime', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_datetime', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_datetime', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Datetime Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_entity_decimal'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_entity_decimal')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_entity_decimal',
-        array('entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_decimal', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_decimal', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_decimal', array('attribute_id')),
-    array('attribute_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_decimal', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_decimal', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_decimal', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Decimal Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_entity_int'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_entity_int')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_entity_int',
-        array('entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_int', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_int', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_int', array('entity_id')),
-    array('entity_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_int', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_int', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_int', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Integer Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_entity_text'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_entity_text')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    '64k',
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_entity_text',
-        array('entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_text', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_text', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_text', array('entity_id')),
-    array('entity_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_text', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_text', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_text', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Text Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_entity_varchar'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_entity_varchar')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_entity_varchar',
-        array('entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_varchar', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_varchar', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_varchar', array('entity_id')),
-    array('entity_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_varchar', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_varchar', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_varchar', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Varchar Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_entity_gallery'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_entity_gallery')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'position',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false, 'default' => '0'),
-    'Position'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array('nullable' => true, 'default' => null),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_entity_gallery',
-        array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_gallery', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_gallery', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_gallery', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_gallery', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_gallery', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_gallery', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Gallery Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_entity'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_entity')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_set_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attriute Set ID'
-)->addColumn(
-    'parent_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Parent Category ID'
-)->addColumn(
-    'created_at',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TIMESTAMP,
-    null,
-    array(),
-    'Creation Time'
-)->addColumn(
-    'updated_at',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TIMESTAMP,
-    null,
-    array(),
-    'Update Time'
-)->addColumn(
-    'path',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array('nullable' => false),
-    'Tree Path'
-)->addColumn(
-    'position',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false),
-    'Position'
-)->addColumn(
-    'level',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false, 'default' => '0'),
-    'Tree Level'
-)->addColumn(
-    'children_count',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false),
-    'Child Count'
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity', array('level')),
-    array('level')
-)->setComment(
-    'Catalog Category Table'
-);
-$installer->getConnection()->createTable($table);
-
-
-/**
- * Create table 'catalog_category_entity_datetime'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_entity_datetime')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DATETIME,
-    null,
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_category_entity_datetime',
-        array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_datetime', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_datetime', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_datetime', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_datetime', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_datetime', 'entity_id', 'catalog_category_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_category_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_datetime', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Category Datetime Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_entity_decimal'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_entity_decimal')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_category_entity_decimal',
-        array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_decimal', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_decimal', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_decimal', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_decimal', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_decimal', 'entity_id', 'catalog_category_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_category_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_decimal', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Category Decimal Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_entity_int'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_entity_int')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_category_entity_int',
-        array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_int', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_int', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_int', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_int', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_int', 'entity_id', 'catalog_category_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_category_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_int', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Category Integer Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_entity_text'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_entity_text')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    '64k',
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_category_entity_text',
-        array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_text', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_text', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_text', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_text', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_text', 'entity_id', 'catalog_category_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_category_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_text', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Category Text Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_entity_varchar'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_entity_varchar')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity Type ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_category_entity_varchar',
-        array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_type_id', 'entity_id', 'attribute_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_varchar', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_varchar', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_category_entity_varchar', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_varchar', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_varchar', 'entity_id', 'catalog_category_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_category_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_entity_varchar', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Category Varchar Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_product'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_product')
-)->addColumn(
-    'category_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Category ID'
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'position',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false, 'default' => '0'),
-    'Position'
-)->addIndex(
-    $installer->getIdxName('catalog_category_product', array('product_id')),
-    array('product_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_category_product', 'category_id', 'catalog_category_entity', 'entity_id'),
-    'category_id',
-    $installer->getTable('catalog_category_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_product', 'product_id', 'catalog_product_entity', 'entity_id'),
-    'product_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product To Category Linkage Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_product_index'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_product_index')
-)->addColumn(
-    'category_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Category ID'
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'position',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true),
-    'Position'
-)->addColumn(
-    'is_parent',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Parent'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'visibility',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false),
-    'Visibility'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_category_product_index',
-        array('product_id', 'store_id', 'category_id', 'visibility')
-    ),
-    array('product_id', 'store_id', 'category_id', 'visibility')
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_category_product_index',
-        array('store_id', 'category_id', 'visibility', 'is_parent', 'position')
-    ),
-    array('store_id', 'category_id', 'visibility', 'is_parent', 'position')
-)->addForeignKey(
-    $installer->getFkName('catalog_category_product_index', 'category_id', 'catalog_category_entity', 'entity_id'),
-    'category_id',
-    $installer->getTable('catalog_category_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_product_index', 'product_id', 'catalog_product_entity', 'entity_id'),
-    'product_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_category_product_index', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Category Product Index'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_compare_item'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_compare_item')
-)->addColumn(
-    'catalog_compare_item_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Compare Item ID'
-)->addColumn(
-    'visitor_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Visitor ID'
-)->addColumn(
-    'customer_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true),
-    'Customer ID'
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true),
-    'Store ID'
-)->addIndex(
-    $installer->getIdxName('catalog_compare_item', array('customer_id')),
-    array('customer_id')
-)->addIndex(
-    $installer->getIdxName('catalog_compare_item', array('product_id')),
-    array('product_id')
-)->addIndex(
-    $installer->getIdxName('catalog_compare_item', array('visitor_id', 'product_id')),
-    array('visitor_id', 'product_id')
-)->addIndex(
-    $installer->getIdxName('catalog_compare_item', array('customer_id', 'product_id')),
-    array('customer_id', 'product_id')
-)->addIndex(
-    $installer->getIdxName('catalog_compare_item', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_compare_item', 'customer_id', 'customer_entity', 'entity_id'),
-    'customer_id',
-    $installer->getTable('customer_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_compare_item', 'product_id', 'catalog_product_entity', 'entity_id'),
-    'product_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_compare_item', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_SET_NULL,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Compare Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_website'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_website')
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Product ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addIndex(
-    $installer->getIdxName('catalog_product_website', array('website_id')),
-    array('website_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_website', 'website_id', 'store_website', 'website_id'),
-    'website_id',
-    $installer->getTable('store_website'),
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_website', 'product_id', 'catalog_product_entity', 'entity_id'),
-    'product_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product To Website Linkage Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_enabled_index'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_enabled_index')
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'visibility',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Visibility'
-)->addIndex(
-    $installer->getIdxName('catalog_product_enabled_index', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_enabled_index', 'product_id', 'catalog_product_entity', 'entity_id'),
-    'product_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_enabled_index', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Visibility Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_link_type'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_link_type')
-)->addColumn(
-    'link_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Link Type ID'
-)->addColumn(
-    'code',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    32,
-    array('nullable' => true, 'default' => null),
-    'Code'
-)->setComment(
-    'Catalog Product Link Type Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_link'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_link')
-)->addColumn(
-    'link_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Link ID'
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'linked_product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Linked Product ID'
-)->addColumn(
-    'link_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Link Type ID'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_link',
-        array('link_type_id', 'product_id', 'linked_product_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('link_type_id', 'product_id', 'linked_product_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_link', array('product_id')),
-    array('product_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_link', array('linked_product_id')),
-    array('linked_product_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_link', array('link_type_id')),
-    array('link_type_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_link', 'linked_product_id', 'catalog_product_entity', 'entity_id'),
-    'linked_product_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_link', 'product_id', 'catalog_product_entity', 'entity_id'),
-    'product_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_link', 'link_type_id', 'catalog_product_link_type', 'link_type_id'),
-    'link_type_id',
-    $installer->getTable('catalog_product_link_type'),
-    'link_type_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product To Product Linkage Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_link_attribute'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_link_attribute')
-)->addColumn(
-    'product_link_attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Product Link Attribute ID'
-)->addColumn(
-    'link_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Link Type ID'
-)->addColumn(
-    'product_link_attribute_code',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    32,
-    array('nullable' => true, 'default' => null),
-    'Product Link Attribute Code'
-)->addColumn(
-    'data_type',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    32,
-    array('nullable' => true, 'default' => null),
-    'Data Type'
-)->addIndex(
-    $installer->getIdxName('catalog_product_link_attribute', array('link_type_id')),
-    array('link_type_id')
-)->addForeignKey(
-    $installer->getFkName(
-        'catalog_product_link_attribute',
-        'link_type_id',
-        'catalog_product_link_type',
-        'link_type_id'
-    ),
-    'link_type_id',
-    $installer->getTable('catalog_product_link_type'),
-    'link_type_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Link Attribute Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_link_attribute_decimal'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_link_attribute_decimal')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'product_link_attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true),
-    'Product Link Attribute ID'
-)->addColumn(
-    'link_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false, 'unsigned' => true),
-    'Link ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array('nullable' => false, 'default' => '0.0000'),
-    'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_link_attribute_decimal', array('product_link_attribute_id')),
-    array('product_link_attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_link_attribute_decimal', array('link_id')),
-    array('link_id')
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_link_attribute_decimal',
-        array('product_link_attribute_id', 'link_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('product_link_attribute_id', 'link_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addForeignKey(
-    $installer->getFkName('catalog_product_link_attribute_decimal', 'link_id', 'catalog_product_link', 'link_id'),
-    'link_id',
-    $installer->getTable('catalog_product_link'),
-    'link_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName(
-        'catalog_product_link_attribute_decimal',
-        'product_link_attribute_id',
-        'catalog_product_link_attribute',
-        'product_link_attribute_id'
-    ),
-    'product_link_attribute_id',
-    $installer->getTable('catalog_product_link_attribute'),
-    'product_link_attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Link Decimal Attribute Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_link_attribute_int'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_link_attribute_int')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'product_link_attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true),
-    'Product Link Attribute ID'
-)->addColumn(
-    'link_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false, 'unsigned' => true),
-    'Link ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false, 'default' => '0'),
-    'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_link_attribute_int', array('product_link_attribute_id')),
-    array('product_link_attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_link_attribute_int', array('link_id')),
-    array('link_id')
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_link_attribute_int',
-        array('product_link_attribute_id', 'link_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('product_link_attribute_id', 'link_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addForeignKey(
-    $installer->getFkName('catalog_product_link_attribute_int', 'link_id', 'catalog_product_link', 'link_id'),
-    'link_id',
-    $installer->getTable('catalog_product_link'),
-    'link_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName(
-        'catalog_product_link_attribute_int',
-        'product_link_attribute_id',
-        'catalog_product_link_attribute',
-        'product_link_attribute_id'
-    ),
-    'product_link_attribute_id',
-    $installer->getTable('catalog_product_link_attribute'),
-    'product_link_attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Link Integer Attribute Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_link_attribute_varchar'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_link_attribute_varchar')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'product_link_attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Product Link Attribute ID'
-)->addColumn(
-    'link_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false, 'unsigned' => true),
-    'Link ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_link_attribute_varchar', array('product_link_attribute_id')),
-    array('product_link_attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_link_attribute_varchar', array('link_id')),
-    array('link_id')
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_link_attribute_varchar',
-        array('product_link_attribute_id', 'link_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('product_link_attribute_id', 'link_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addForeignKey(
-    $installer->getFkName('catalog_product_link_attribute_varchar', 'link_id', 'catalog_product_link', 'link_id'),
-    'link_id',
-    $installer->getTable('catalog_product_link'),
-    'link_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName(
-        'catalog_product_link_attribute_varchar',
-        'product_link_attribute_id',
-        'catalog_product_link_attribute',
-        'product_link_attribute_id'
-    ),
-    'product_link_attribute_id',
-    $installer->getTable('catalog_product_link_attribute'),
-    'product_link_attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Link Varchar Attribute Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_entity_tier_price'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_entity_tier_price')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'all_groups',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '1'),
-    'Is Applicable To All Customer Groups'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Customer Group ID'
-)->addColumn(
-    'qty',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array('nullable' => false, 'default' => '1.0000'),
-    'QTY'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array('nullable' => false, 'default' => '0.0000'),
-    'Value'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false),
-    'Website ID'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_entity_tier_price',
-        array('entity_id', 'all_groups', 'customer_group_id', 'qty', 'website_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('entity_id', 'all_groups', 'customer_group_id', 'qty', 'website_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_tier_price', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_tier_price', array('customer_group_id')),
-    array('customer_group_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_tier_price', array('website_id')),
-    array('website_id')
-)->addForeignKey(
-    $installer->getFkName(
-        'catalog_product_entity_tier_price',
-        'customer_group_id',
-        'customer_group',
-        'customer_group_id'
-    ),
-    'customer_group_id',
-    $installer->getTable('customer_group'),
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_tier_price', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_tier_price', 'website_id', 'store_website', 'website_id'),
-    'website_id',
-    $installer->getTable('store_website'),
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Tier Price Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_entity_media_gallery'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_entity_media_gallery')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Value ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Attribute ID'
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Entity ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array(),
-    'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_media_gallery', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_media_gallery', array('entity_id')),
-    array('entity_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_media_gallery', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_media_gallery', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Media Gallery Attribute Backend Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_entity_media_gallery_value'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_entity_media_gallery_value')
-)->addColumn(
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Value ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'label',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array(),
-    'Label'
-)->addColumn(
-    'position',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true),
-    'Position'
-)->addColumn(
-    'disabled',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Disabled'
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_media_gallery_value', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName(
-        'catalog_product_entity_media_gallery_value',
-        'value_id',
-        'catalog_product_entity_media_gallery',
-        'value_id'
-    ),
-    'value_id',
-    $installer->getTable('catalog_product_entity_media_gallery'),
-    'value_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_entity_media_gallery_value', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Media Gallery Attribute Value Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_option'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_option')
-)->addColumn(
-    'option_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Option ID'
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'type',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    50,
-    array('nullable' => true, 'default' => null),
-    'Type'
-)->addColumn(
-    'is_require',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('nullable' => false, 'default' => '1'),
-    'Is Required'
-)->addColumn(
-    'sku',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    64,
-    array(),
-    'SKU'
-)->addColumn(
-    'max_characters',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true),
-    'Max Characters'
-)->addColumn(
-    'file_extension',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    50,
-    array(),
-    'File Extension'
-)->addColumn(
-    'image_size_x',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true),
-    'Image Size X'
-)->addColumn(
-    'image_size_y',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true),
-    'Image Size Y'
-)->addColumn(
-    'sort_order',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Sort Order'
-)->addIndex(
-    $installer->getIdxName('catalog_product_option', array('product_id')),
-    array('product_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_option', 'product_id', 'catalog_product_entity', 'entity_id'),
-    'product_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Option Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_option_price'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_option_price')
-)->addColumn(
-    'option_price_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Option Price ID'
-)->addColumn(
-    'option_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Option ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array('nullable' => false, 'default' => '0.0000'),
-    'Price'
-)->addColumn(
-    'price_type',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    7,
-    array('nullable' => false, 'default' => 'fixed'),
-    'Price Type'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_option_price',
-        array('option_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('option_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_price', array('option_id')),
-    array('option_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_price', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_option_price', 'option_id', 'catalog_product_option', 'option_id'),
-    'option_id',
-    $installer->getTable('catalog_product_option'),
-    'option_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_option_price', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Option Price Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_option_title'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_option_title')
-)->addColumn(
-    'option_title_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Option Title ID'
-)->addColumn(
-    'option_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Option ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'title',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array('nullable' => true, 'default' => null),
-    'Title'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_option_title',
-        array('option_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('option_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_title', array('option_id')),
-    array('option_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_title', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_option_title', 'option_id', 'catalog_product_option', 'option_id'),
-    'option_id',
-    $installer->getTable('catalog_product_option'),
-    'option_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_option_title', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Option Title Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_option_type_value'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_option_type_value')
-)->addColumn(
-    'option_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Option Type ID'
-)->addColumn(
-    'option_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Option ID'
-)->addColumn(
-    'sku',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    64,
-    array(),
-    'SKU'
-)->addColumn(
-    'sort_order',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Sort Order'
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_type_value', array('option_id')),
-    array('option_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_option_type_value', 'option_id', 'catalog_product_option', 'option_id'),
-    'option_id',
-    $installer->getTable('catalog_product_option'),
-    'option_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Option Type Value Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_option_type_price'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_option_type_price')
-)->addColumn(
-    'option_type_price_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Option Type Price ID'
-)->addColumn(
-    'option_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Option Type ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array('nullable' => false, 'default' => '0.0000'),
-    'Price'
-)->addColumn(
-    'price_type',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    7,
-    array('nullable' => false, 'default' => 'fixed'),
-    'Price Type'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_option_type_price',
-        array('option_type_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('option_type_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_type_price', array('option_type_id')),
-    array('option_type_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_type_price', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName(
-        'catalog_product_option_type_price',
-        'option_type_id',
-        'catalog_product_option_type_value',
-        'option_type_id'
-    ),
-    'option_type_id',
-    $installer->getTable('catalog_product_option_type_value'),
-    'option_type_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_option_type_price', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Option Type Price Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_option_type_title'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_option_type_title')
-)->addColumn(
-    'option_type_title_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Option Type Title ID'
-)->addColumn(
-    'option_type_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Option Type ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'title',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array('nullable' => true, 'default' => null),
-    'Title'
-)->addIndex(
-    $installer->getIdxName(
-        'catalog_product_option_type_title',
-        array('option_type_id', 'store_id'),
-        \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE
-    ),
-    array('option_type_id', 'store_id'),
-    array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_type_title', array('option_type_id')),
-    array('option_type_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_option_type_title', array('store_id')),
-    array('store_id')
-)->addForeignKey(
-    $installer->getFkName(
-        'catalog_product_option_type_title',
-        'option_type_id',
-        'catalog_product_option_type_value',
-        'option_type_id'
-    ),
-    'option_type_id',
-    $installer->getTable('catalog_product_option_type_value'),
-    'option_type_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_option_type_title', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Option Type Title Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_eav_attribute'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_eav_attribute')
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Attribute ID'
-)->addColumn(
-    'frontend_input_renderer',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array(),
-    'Frontend Input Renderer'
-)->addColumn(
-    'is_global',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '1'),
-    'Is Global'
-)->addColumn(
-    'is_visible',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '1'),
-    'Is Visible'
-)->addColumn(
-    'is_searchable',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Searchable'
-)->addColumn(
-    'is_filterable',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Filterable'
-)->addColumn(
-    'is_comparable',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Comparable'
-)->addColumn(
-    'is_visible_on_front',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Visible On Front'
-)->addColumn(
-    'is_html_allowed_on_front',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is HTML Allowed On Front'
-)->addColumn(
-    'is_used_for_price_rules',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Used For Price Rules'
-)->addColumn(
-    'is_filterable_in_search',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Filterable In Search'
-)->addColumn(
-    'used_in_product_listing',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Used In Product Listing'
-)->addColumn(
-    'used_for_sort_by',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Used For Sorting'
-)->addColumn(
-    'apply_to',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array('nullable' => true),
-    'Apply To'
-)->addColumn(
-    'is_visible_in_advanced_search',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Visible In Advanced Search'
-)->addColumn(
-    'position',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false, 'default' => '0'),
-    'Position'
-)->addColumn(
-    'is_wysiwyg_enabled',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is WYSIWYG Enabled'
-)->addColumn(
-    'is_used_for_promo_rules',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Used For Promo Rules'
-)->addIndex(
-    $installer->getIdxName('catalog_eav_attribute', array('used_for_sort_by')),
-    array('used_for_sort_by')
-)->addIndex(
-    $installer->getIdxName('catalog_eav_attribute', array('used_in_product_listing')),
-    array('used_in_product_listing')
-)->addForeignKey(
-    $installer->getFkName('catalog_eav_attribute', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog EAV Attribute Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_relation'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_relation')
-)->addColumn(
-    'parent_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Parent ID'
-)->addColumn(
-    'child_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Child ID'
-)->addIndex(
-    $installer->getIdxName('catalog_product_relation', array('child_id')),
-    array('child_id')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_relation', 'child_id', 'catalog_product_entity', 'entity_id'),
-    'child_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_relation', 'parent_id', 'catalog_product_entity', 'entity_id'),
-    'parent_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Relation Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_eav'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_eav')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Store ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav', array('value')),
-    array('value')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_eav', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_eav', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_eav', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product EAV Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_eav_decimal'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_eav_decimal')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Store ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array('nullable' => false, 'primary' => true),
-    'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal', array('value')),
-    array('value')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_eav_decimal', 'attribute_id', 'eav_attribute', 'attribute_id'),
-    'attribute_id',
-    $installer->getTable('eav_attribute'),
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_eav_decimal', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_eav_decimal', 'store_id', 'store', 'store_id'),
-    'store_id',
-    $installer->getTable('store'),
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product EAV Decimal Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'tax_class_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'default' => '0'),
-    'Tax Class ID'
-)->addColumn(
-    'price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Price'
-)->addColumn(
-    'final_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Final Price'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_price', array('customer_group_id')),
-    array('customer_group_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_price', array('website_id')),
-    array('website_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_price', array('min_price')),
-    array('min_price')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_price', 'customer_group_id', 'customer_group', 'customer_group_id'),
-    'customer_group_id',
-    $installer->getTable('customer_group'),
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_price', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_price', 'website_id', 'store_website', 'website_id'),
-    'website_id',
-    $installer->getTable('store_website'),
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Price Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_tier_price'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_tier_price')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_tier_price', array('customer_group_id')),
-    array('customer_group_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_tier_price', array('website_id')),
-    array('website_id')
-)->addForeignKey(
-    $installer->getFkName(
-        'catalog_product_index_tier_price',
-        'customer_group_id',
-        'customer_group',
-        'customer_group_id'
-    ),
-    'customer_group_id',
-    $installer->getTable('customer_group'),
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_tier_price', 'entity_id', 'catalog_product_entity', 'entity_id'),
-    'entity_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_tier_price', 'website_id', 'store_website', 'website_id'),
-    'website_id',
-    $installer->getTable('store_website'),
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Tier Price Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_website'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_website')
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'website_date',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DATE,
-    null,
-    array(),
-    'Website Date'
-)->addColumn(
-    'rate',
-    \Magento\Framework\DB\Ddl\Table::TYPE_FLOAT,
-    null,
-    array('default' => '1.0000'),
-    'Rate'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_website', array('website_date')),
-    array('website_date')
-)->addForeignKey(
-    $installer->getFkName('catalog_product_index_website', 'website_id', 'store_website', 'website_id'),
-    'website_id',
-    $installer->getTable('store_website'),
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE,
-    \Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
-)->setComment(
-    'Catalog Product Website Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_cfg_opt_agr_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_cfg_opt_agr_idx')
-)->addColumn(
-    'parent_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Parent ID'
-)->addColumn(
-    'child_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Child ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->setComment(
-    'Catalog Product Price Indexer Config Option Aggregate Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_cfg_opt_agr_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_cfg_opt_agr_tmp')
-)->addColumn(
-    'parent_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Parent ID'
-)->addColumn(
-    'child_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Child ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->setComment(
-    'Catalog Product Price Indexer Config Option Aggregate Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_cfg_opt_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_cfg_opt_idx')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->setComment(
-    'Catalog Product Price Indexer Config Option Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_cfg_opt_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_cfg_opt_tmp')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->setComment(
-    'Catalog Product Price Indexer Config Option Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_final_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_final_idx')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'tax_class_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'default' => '0'),
-    'Tax Class ID'
-)->addColumn(
-    'orig_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Original Price'
-)->addColumn(
-    'price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Price'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->addColumn(
-    'base_tier',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Base Tier'
-)->setComment(
-    'Catalog Product Price Indexer Final Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_final_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_final_tmp')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'tax_class_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'default' => '0'),
-    'Tax Class ID'
-)->addColumn(
-    'orig_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Original Price'
-)->addColumn(
-    'price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Price'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->addColumn(
-    'base_tier',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Base Tier'
-)->setComment(
-    'Catalog Product Price Indexer Final Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_opt_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_opt_idx')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->setComment(
-    'Catalog Product Price Indexer Option Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_opt_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_opt_tmp')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->setComment(
-    'Catalog Product Price Indexer Option Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_opt_agr_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_opt_agr_idx')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'option_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Option ID'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->setComment(
-    'Catalog Product Price Indexer Option Aggregate Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_opt_agr_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_opt_agr_tmp')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'option_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
-    'Option ID'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->setComment(
-    'Catalog Product Price Indexer Option Aggregate Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_eav_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_eav_idx')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Store ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_idx', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_idx', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_idx', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_idx', array('value')),
-    array('value')
-)->setComment(
-    'Catalog Product EAV Indexer Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_eav_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_eav_tmp')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Store ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_tmp', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_tmp', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_tmp', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_tmp', array('value')),
-    array('value')
-)->setComment(
-    'Catalog Product EAV Indexer Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_eav_decimal_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_eav_decimal_idx')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Store ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array('nullable' => false, 'primary' => true),
-    'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal_idx', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal_idx', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal_idx', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal_idx', array('value')),
-    array('value')
-)->setComment(
-    'Catalog Product EAV Decimal Indexer Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_eav_decimal_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_eav_decimal_tmp')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'attribute_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Attribute ID'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Store ID'
-)->addColumn(
-    'value',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array('nullable' => false, 'primary' => true),
-    'Value'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal_tmp', array('entity_id')),
-    array('entity_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal_tmp', array('attribute_id')),
-    array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal_tmp', array('store_id')),
-    array('store_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_eav_decimal_tmp', array('value')),
-    array('value')
-)->setComment(
-    'Catalog Product EAV Decimal Indexer Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_idx')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'tax_class_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'default' => '0'),
-    'Tax Class ID'
-)->addColumn(
-    'price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Price'
-)->addColumn(
-    'final_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Final Price'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_price_idx', array('customer_group_id')),
-    array('customer_group_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_price_idx', array('website_id')),
-    array('website_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_price_idx', array('min_price')),
-    array('min_price')
-)->setComment(
-    'Catalog Product Price Indexer Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_product_index_price_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_product_index_price_tmp')
-)->addColumn(
-    'entity_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Entity ID'
-)->addColumn(
-    'customer_group_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Customer Group ID'
-)->addColumn(
-    'website_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'primary' => true),
-    'Website ID'
-)->addColumn(
-    'tax_class_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'default' => '0'),
-    'Tax Class ID'
-)->addColumn(
-    'price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Price'
-)->addColumn(
-    'final_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Final Price'
-)->addColumn(
-    'min_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Min Price'
-)->addColumn(
-    'max_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Max Price'
-)->addColumn(
-    'tier_price',
-    \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL,
-    '12,4',
-    array(),
-    'Tier Price'
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_price_tmp', array('customer_group_id')),
-    array('customer_group_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_price_tmp', array('website_id')),
-    array('website_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_index_price_tmp', array('min_price')),
-    array('min_price')
-)->setComment(
-    'Catalog Product Price Indexer Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_product_index_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_product_index_idx')
-)->addColumn(
-    'category_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Category ID'
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'position',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false, 'default' => '0'),
-    'Position'
-)->addColumn(
-    'is_parent',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Parent'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'visibility',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false),
-    'Visibility'
-)->addIndex(
-    $installer->getIdxName('catalog_category_product_index_idx', array('product_id', 'category_id', 'store_id')),
-    array('product_id', 'category_id', 'store_id')
-)->setComment(
-    'Catalog Category Product Indexer Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_product_index_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_product_index_tmp')
-)->addColumn(
-    'category_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Category ID'
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'position',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('nullable' => false, 'default' => '0'),
-    'Position'
-)->addColumn(
-    'is_parent',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Is Parent'
-)->addColumn(
-    'store_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Store ID'
-)->addColumn(
-    'visibility',
-    \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT,
-    null,
-    array('unsigned' => true, 'nullable' => false),
-    'Visibility'
-)->setComment(
-    'Catalog Category Product Indexer Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_product_index_enbl_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_product_index_enbl_idx')
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'visibility',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Visibility'
-)->addIndex(
-    $installer->getIdxName('catalog_category_product_index_enbl_idx', array('product_id')),
-    array('product_id')
-)->setComment(
-    'Catalog Category Product Enabled Indexer Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_product_index_enbl_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_product_index_enbl_tmp')
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'visibility',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Visibility'
-)->addIndex(
-    $installer->getIdxName('catalog_category_product_index_enbl_tmp', array('product_id')),
-    array('product_id')
-)->setComment(
-    'Catalog Category Product Enabled Indexer Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_anc_categs_index_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_anc_categs_index_idx')
-)->addColumn(
-    'category_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Category ID'
-)->addColumn(
-    'path',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array('nullable' => true, 'default' => null),
-    'Path'
-)->addIndex(
-    $installer->getIdxName('catalog_category_anc_categs_index_idx', array('category_id')),
-    array('category_id')
-)->setComment(
-    'Catalog Category Anchor Indexer Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_anc_categs_index_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_anc_categs_index_tmp')
-)->addColumn(
-    'category_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Category ID'
-)->addColumn(
-    'path',
-    \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
-    255,
-    array('nullable' => true, 'default' => null),
-    'Path'
-)->addIndex(
-    $installer->getIdxName('catalog_category_anc_categs_index_tmp', array('category_id')),
-    array('category_id')
-)->setComment(
-    'Catalog Category Anchor Indexer Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_anc_products_index_idx'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_anc_products_index_idx')
-)->addColumn(
-    'category_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Category ID'
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Product ID'
-)->addColumn(
-    'position',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true),
-    'Position'
-)->setComment(
-    'Catalog Category Anchor Product Indexer Index Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Create table 'catalog_category_anc_products_index_tmp'
- */
-$table = $installer->getConnection()->newTable(
-    $installer->getTable('catalog_category_anc_products_index_tmp')
-)->addColumn(
-    'category_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Category ID'
-)->addColumn(
-    'product_id',
-    \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-    null,
-    array('unsigned' => true, 'nullable' => false, 'default' => '0'),
-    'Product ID'
-)->setComment(
-    'Catalog Category Anchor Product Indexer Temp Table'
-);
-$installer->getConnection()->createTable($table);
-
-/**
- * Modify core/url_rewrite table
- */
-$installer->getConnection()->addColumn(
-    $installer->getTable('core_url_rewrite'),
-    'category_id',
-    array(
-        'type' => \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-        'unsigned' => true,
-        'nullable' => true,
-        'comment' => 'Category Id'
-    )
-);
-$installer->getConnection()->addColumn(
-    $installer->getTable('core_url_rewrite'),
-    'product_id',
-    array(
-        'type' => \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
-        'unsigned' => true,
-        'nullable' => true,
-        'comment' => 'Product Id'
-    )
-);
-$installer->getConnection()->addForeignKey(
-    $installer->getFkName('core_url_rewrite', 'category_id', 'catalog_category_entity', 'entity_id'),
-    $installer->getTable('core_url_rewrite'),
-    'category_id',
-    $installer->getTable('catalog_category_entity'),
-    'entity_id'
-);
-$installer->getConnection()->addForeignKey(
-    $installer->getFkName('core_url_rewrite', 'product_id', 'catalog_category_entity', 'entity_id'),
-    $installer->getTable('core_url_rewrite'),
-    'product_id',
-    $installer->getTable('catalog_product_entity'),
-    'entity_id'
-);
-
-$installer->endSetup();
-
-$installer->installEntities();
diff --git a/app/code/Magento/Catalog/sql/catalog_setup/upgrade-1.6.0.0.7-1.6.0.0.8.php b/app/code/Magento/Catalog/sql/catalog_setup/upgrade-1.6.0.0.7-1.6.0.0.8.php
index ab224dc5898..cf82005f2b4 100644
--- a/app/code/Magento/Catalog/sql/catalog_setup/upgrade-1.6.0.0.7-1.6.0.0.8.php
+++ b/app/code/Magento/Catalog/sql/catalog_setup/upgrade-1.6.0.0.7-1.6.0.0.8.php
@@ -72,9 +72,3 @@ $connection->addIndex(
     $installer->getIdxName('catalog_category_anc_categs_index_tmp', array('path', 'category_id')),
     array('path', 'category_id')
 );
-
-$connection->addIndex(
-    $installer->getTable('catalog_category_entity'),
-    $installer->getIdxName('catalog_category_entity', array('path', 'entity_id')),
-    array('path', 'entity_id')
-);
diff --git a/app/code/Magento/Catalog/sql/catalog_setup/upgrade-1.6.0.0.9-1.6.0.0.10.php b/app/code/Magento/Catalog/sql/catalog_setup/upgrade-1.6.0.0.9-1.6.0.0.10.php
index 72e4594ebc1..b715610f8df 100644
--- a/app/code/Magento/Catalog/sql/catalog_setup/upgrade-1.6.0.0.9-1.6.0.0.10.php
+++ b/app/code/Magento/Catalog/sql/catalog_setup/upgrade-1.6.0.0.9-1.6.0.0.10.php
@@ -75,9 +75,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('entity_id', 'all_groups', 'customer_group_id', 'website_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_entity_group_price', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_entity_group_price', array('customer_group_id')),
     array('customer_group_id')
diff --git a/app/code/Magento/Catalog/view/adminhtml/templates/catalog/product/edit/options/type/file.phtml b/app/code/Magento/Catalog/view/adminhtml/templates/catalog/product/edit/options/type/file.phtml
index 53e4756b71a..d51869aa4c2 100644
--- a/app/code/Magento/Catalog/view/adminhtml/templates/catalog/product/edit/options/type/file.phtml
+++ b/app/code/Magento/Catalog/view/adminhtml/templates/catalog/product/edit/options/type/file.phtml
@@ -57,10 +57,10 @@
                 <td>
                     <input name="product[options][${option_id}][file_extension]" class="input-text" type="text" value="${file_extension}">
                 </td>
-                <td class="col-file"><?php echo __('%1 x %2 px.',
+                <td class="col-file"><?php echo __('%1 <span>x</span> %2 <span>px.</span>',
                     '<input class="input-text" type="text" name="product[options][${option_id}][image_size_x]" value="${image_size_x}">',
                     '<input class="input-text" type="text" name="product[options][${option_id}][image_size_y]" value="${image_size_y}">') ?>
-                    <br/><?php echo __('Please leave blank if it is not an image.') ?>
+                    <div class="note"><?php echo __('Please leave blank if it is not an image.') ?></div>
                 </td>
             </tr>
         </table>
diff --git a/app/code/Magento/CatalogInventory/Block/Qtyincrements.php b/app/code/Magento/CatalogInventory/Block/Qtyincrements.php
index 4e3dd1b0a7f..947ef525c3b 100644
--- a/app/code/Magento/CatalogInventory/Block/Qtyincrements.php
+++ b/app/code/Magento/CatalogInventory/Block/Qtyincrements.php
@@ -22,17 +22,14 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-
-/**
- * Product qty increments block
- *
- * @author      Magento Core Team <core@magentocommerce.com>
- */
 namespace Magento\CatalogInventory\Block;
 
 use Magento\Framework\View\Element\Template;
 use Magento\Framework\View\Block\IdentityInterface;
 
+/**
+ * Product qty increments block
+ */
 class Qtyincrements extends Template implements IdentityInterface
 {
     /**
@@ -47,19 +44,27 @@ class Qtyincrements extends Template implements IdentityInterface
      *
      * @var \Magento\Framework\Registry
      */
-    protected $_coreRegistry = null;
+    protected $_coreRegistry;
+
+    /**
+     * @var \Magento\CatalogInventory\Service\V1\StockItem
+     */
+    protected $stockItemService;
 
     /**
      * @param \Magento\Framework\View\Element\Template\Context $context
      * @param \Magento\Framework\Registry $registry
+     * @param \Magento\CatalogInventory\Service\V1\StockItem $stockItemService
      * @param array $data
      */
     public function __construct(
         \Magento\Framework\View\Element\Template\Context $context,
         \Magento\Framework\Registry $registry,
+        \Magento\CatalogInventory\Service\V1\StockItem $stockItemService,
         array $data = array()
     ) {
         $this->_coreRegistry = $registry;
+        $this->stockItemService = $stockItemService;
         parent::__construct($context, $data);
     }
 
@@ -91,7 +96,7 @@ class Qtyincrements extends Template implements IdentityInterface
     public function getProductQtyIncrements()
     {
         if ($this->_qtyIncrements === null) {
-            $this->_qtyIncrements = $this->getProduct()->getStockItem()->getQtyIncrements();
+            $this->_qtyIncrements = $this->stockItemService->getQtyIncrements($this->getProduct()->getId());
             if (!$this->getProduct()->isSaleable()) {
                 $this->_qtyIncrements = false;
             }
diff --git a/app/code/Magento/CatalogInventory/Block/Stockqty/AbstractStockqty.php b/app/code/Magento/CatalogInventory/Block/Stockqty/AbstractStockqty.php
index a8a6759c689..ac375618d61 100644
--- a/app/code/Magento/CatalogInventory/Block/Stockqty/AbstractStockqty.php
+++ b/app/code/Magento/CatalogInventory/Block/Stockqty/AbstractStockqty.php
@@ -22,16 +22,18 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
+namespace Magento\CatalogInventory\Block\Stockqty;
+
+use Magento\Catalog\Model\Product;
 
 /**
- * Product stock qty abstarct block
- *
- * @author      Magento Core Team <core@magentocommerce.com>
+ * Product stock qty abstract block
  */
-namespace Magento\CatalogInventory\Block\Stockqty;
-
 abstract class AbstractStockqty extends \Magento\Framework\View\Element\Template
 {
+    /**
+     * Threshold qty config path
+     */
     const XML_PATH_STOCK_THRESHOLD_QTY = 'cataloginventory/options/stock_threshold_qty';
 
     /**
@@ -39,19 +41,27 @@ abstract class AbstractStockqty extends \Magento\Framework\View\Element\Template
      *
      * @var \Magento\Framework\Registry
      */
-    protected $_coreRegistry = null;
+    protected $_coreRegistry;
+
+    /**
+     * @var \Magento\CatalogInventory\Service\V1\StockItem
+     */
+    protected $stockItemService;
 
     /**
      * @param \Magento\Framework\View\Element\Template\Context $context
      * @param \Magento\Framework\Registry $registry
+     * @param \Magento\CatalogInventory\Service\V1\StockItem $stockItemService
      * @param array $data
      */
     public function __construct(
         \Magento\Framework\View\Element\Template\Context $context,
         \Magento\Framework\Registry $registry,
+        \Magento\CatalogInventory\Service\V1\StockItem $stockItemService,
         array $data = array()
     ) {
         $this->_coreRegistry = $registry;
+        $this->stockItemService = $stockItemService;
         parent::__construct($context, $data);
     }
 
@@ -74,15 +84,26 @@ abstract class AbstractStockqty extends \Magento\Framework\View\Element\Template
     {
         if (!$this->hasData('product_stock_qty')) {
             $qty = 0;
-            $stockItem = $this->getProduct()->getStockItem();
-            if ($stockItem) {
-                $qty = (double)$stockItem->getStockQty();
+            $productId = $this->getProduct()->getId();
+            if ($productId) {
+                $qty = $this->getProductStockQty($this->getProduct());
             }
             $this->setData('product_stock_qty', $qty);
         }
         return $this->getData('product_stock_qty');
     }
 
+    /**
+     * Retrieve product stock qty
+     *
+     * @param Product $product
+     * @return float
+     */
+    public function getProductStockQty($product)
+    {
+        return $this->stockItemService->getStockQty($product->getId());
+    }
+
     /**
      * Retrieve threshold of qty to display stock qty message
      *
@@ -91,7 +112,7 @@ abstract class AbstractStockqty extends \Magento\Framework\View\Element\Template
     public function getThresholdQty()
     {
         if (!$this->hasData('threshold_qty')) {
-            $qty = (double)$this->_scopeConfig->getValue(
+            $qty = (float) $this->_scopeConfig->getValue(
                 self::XML_PATH_STOCK_THRESHOLD_QTY,
                 \Magento\Store\Model\ScopeInterface::SCOPE_STORE
             );
diff --git a/app/code/Magento/CatalogInventory/Block/Stockqty/Composite.php b/app/code/Magento/CatalogInventory/Block/Stockqty/Composite.php
index 67eb4e257c7..ef60d876d0d 100644
--- a/app/code/Magento/CatalogInventory/Block/Stockqty/Composite.php
+++ b/app/code/Magento/CatalogInventory/Block/Stockqty/Composite.php
@@ -22,16 +22,13 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-
-/**
- * Product stock qty block for abstract composite product
- *
- * @author      Magento Core Team <core@magentocommerce.com>
- */
 namespace Magento\CatalogInventory\Block\Stockqty;
 
 use Magento\Catalog\Model\Product;
 
+/**
+ * Product stock qty block for abstract composite product
+ */
 abstract class Composite extends DefaultStockqty
 {
     /**
@@ -61,17 +58,6 @@ abstract class Composite extends DefaultStockqty
         return $this->_childProducts;
     }
 
-    /**
-     * Retrieve product stock qty
-     *
-     * @param Product $product
-     * @return float
-     */
-    public function getProductStockQty($product)
-    {
-        return $product->getStockItem()->getStockQty();
-    }
-
     /**
      * Retrieve id of details table placeholder in template
      *
diff --git a/app/code/Magento/CatalogInventory/Block/Stockqty/DefaultStockqty.php b/app/code/Magento/CatalogInventory/Block/Stockqty/DefaultStockqty.php
index 8bf999dbd81..526c353e7b0 100644
--- a/app/code/Magento/CatalogInventory/Block/Stockqty/DefaultStockqty.php
+++ b/app/code/Magento/CatalogInventory/Block/Stockqty/DefaultStockqty.php
@@ -22,14 +22,11 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
+namespace Magento\CatalogInventory\Block\Stockqty;
 
 /**
  * Product stock qty default block
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
-namespace Magento\CatalogInventory\Block\Stockqty;
-
 class DefaultStockqty extends AbstractStockqty implements \Magento\Framework\View\Block\IdentityInterface
 {
     /**
diff --git a/app/code/Magento/CatalogInventory/Block/Stockqty/Type/Grouped.php b/app/code/Magento/CatalogInventory/Block/Stockqty/Type/Grouped.php
index 66916543f97..0fa00fd4eb4 100644
--- a/app/code/Magento/CatalogInventory/Block/Stockqty/Type/Grouped.php
+++ b/app/code/Magento/CatalogInventory/Block/Stockqty/Type/Grouped.php
@@ -22,16 +22,13 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-
-/**
- * Product stock qty block for grouped product type
- *
- * @author      Magento Core Team <core@magentocommerce.com>
- */
 namespace Magento\CatalogInventory\Block\Stockqty\Type;
 
 use Magento\Catalog\Model\Product;
 
+/**
+ * Product stock qty block for grouped product type
+ */
 class Grouped extends \Magento\CatalogInventory\Block\Stockqty\Composite
 {
     /**
diff --git a/app/code/Magento/CatalogInventory/Helper/Data.php b/app/code/Magento/CatalogInventory/Helper/Data.php
index 87fb2d4a490..cf88006dc27 100644
--- a/app/code/Magento/CatalogInventory/Helper/Data.php
+++ b/app/code/Magento/CatalogInventory/Helper/Data.php
@@ -22,15 +22,21 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-/**
- * Catalo
- */
 namespace Magento\CatalogInventory\Helper;
 
+/**
+ * Catalog Inventory default helper
+ */
 class Data extends \Magento\Framework\App\Helper\AbstractHelper
 {
+    /**
+     * Show out of stock config path
+     */
     const XML_PATH_SHOW_OUT_OF_STOCK = 'cataloginventory/options/show_out_of_stock';
 
+    /**
+     * Auto return config path
+     */
     const XML_PATH_ITEM_AUTO_RETURN = 'cataloginventory/item_options/auto_return';
 
     /**
@@ -43,26 +49,17 @@ class Data extends \Magento\Framework\App\Helper\AbstractHelper
      */
     const ERROR_QTY = 1;
 
-    const ERROR_QTY_INCREMENTS = 2;
-
-    /**
-     * All product types registry in scope of quantity availability
-     *
-     * @var array
-     */
-    protected static $_isQtyTypeIds;
-
     /**
-     * @var \Magento\Catalog\Model\ProductTypes\ConfigInterface
+     * Error qty increments
      */
-    protected $_config;
+    const ERROR_QTY_INCREMENTS = 2;
 
     /**
      * Core store config
      *
      * @var \Magento\Framework\App\Config\ScopeConfigInterface
      */
-    protected $_scopeConfig;
+    protected $scopeConfig;
 
     /**
      * @param \Magento\Framework\App\Helper\Context $context
@@ -71,56 +68,12 @@ class Data extends \Magento\Framework\App\Helper\AbstractHelper
      */
     public function __construct(
         \Magento\Framework\App\Helper\Context $context,
-        \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig,
-        \Magento\Catalog\Model\ProductTypes\ConfigInterface $config
+        \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig
     ) {
-        $this->_config = $config;
-        $this->_scopeConfig = $scopeConfig;
+        $this->scopeConfig = $scopeConfig;
         parent::__construct($context);
     }
 
-    /**
-     * Check if quantity defined for specified product type
-     *
-     * @param string $productTypeId
-     * @return bool
-     */
-    public function isQty($productTypeId)
-    {
-        $this->getIsQtyTypeIds();
-        if (!isset(self::$_isQtyTypeIds[$productTypeId])) {
-            return false;
-        }
-        return self::$_isQtyTypeIds[$productTypeId];
-    }
-
-    /**
-     * Get all registered product type ids and if quantity is defined for them
-     *
-     * @param bool $filter
-     * @return array
-     */
-    public function getIsQtyTypeIds($filter = null)
-    {
-        if (null === self::$_isQtyTypeIds) {
-            self::$_isQtyTypeIds = array();
-
-            foreach ($this->_config->getAll() as $typeId => $typeConfig) {
-                self::$_isQtyTypeIds[$typeId] = isset($typeConfig['is_qty']) ? $typeConfig['is_qty'] : false;
-            }
-        }
-        if (null === $filter) {
-            return self::$_isQtyTypeIds;
-        }
-        $result = self::$_isQtyTypeIds;
-        foreach ($result as $key => $value) {
-            if ($value !== $filter) {
-                unset($result[$key]);
-            }
-        }
-        return $result;
-    }
-
     /**
      * Retrieve inventory item options (used in config)
      *
@@ -148,7 +101,10 @@ class Data extends \Magento\Framework\App\Helper\AbstractHelper
      */
     public function isShowOutOfStock()
     {
-        return $this->_scopeConfig->isSetFlag(self::XML_PATH_SHOW_OUT_OF_STOCK, \Magento\Store\Model\ScopeInterface::SCOPE_STORE);
+        return $this->scopeConfig->isSetFlag(
+            self::XML_PATH_SHOW_OUT_OF_STOCK,
+            \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+        );
     }
 
     /**
@@ -158,7 +114,10 @@ class Data extends \Magento\Framework\App\Helper\AbstractHelper
      */
     public function isAutoReturnEnabled()
     {
-        return $this->_scopeConfig->isSetFlag(self::XML_PATH_ITEM_AUTO_RETURN, \Magento\Store\Model\ScopeInterface::SCOPE_STORE);
+        return $this->scopeConfig->isSetFlag(
+            self::XML_PATH_ITEM_AUTO_RETURN,
+            \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+        );
     }
 
     /**
@@ -169,6 +128,9 @@ class Data extends \Magento\Framework\App\Helper\AbstractHelper
      */
     public function isDisplayProductStockStatus()
     {
-        return $this->_scopeConfig->isSetFlag(self::XML_PATH_DISPLAY_PRODUCT_STOCK_STATUS, \Magento\Store\Model\ScopeInterface::SCOPE_STORE);
+        return $this->scopeConfig->isSetFlag(
+            self::XML_PATH_DISPLAY_PRODUCT_STOCK_STATUS,
+            \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+        );
     }
 }
diff --git a/app/code/Magento/CatalogInventory/Helper/Minsaleqty.php b/app/code/Magento/CatalogInventory/Helper/Minsaleqty.php
index b892deda6c8..e2adf1a3ad1 100644
--- a/app/code/Magento/CatalogInventory/Helper/Minsaleqty.php
+++ b/app/code/Magento/CatalogInventory/Helper/Minsaleqty.php
@@ -22,14 +22,14 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-/**
- * MinSaleQty value manipulation helper
- */
 namespace Magento\CatalogInventory\Helper;
 
 use Magento\Store\Model\Store;
 use Magento\Customer\Service\V1\CustomerGroupServiceInterface as CustomerGroupService;
 
+/**
+ * MinSaleQty value manipulation helper
+ */
 class Minsaleqty
 {
     /**
@@ -64,7 +64,7 @@ class Minsaleqty
      */
     protected function _fixQty($qty)
     {
-        return !empty($qty) ? (double)$qty : null;
+        return !empty($qty) ? (float) $qty : null;
     }
 
     /**
@@ -86,7 +86,7 @@ class Minsaleqty
                 }
             }
             if (count($data) == 1 && array_key_exists(CustomerGroupService::CUST_GROUP_ALL, $data)) {
-                return (string)$data[CustomerGroupService::CUST_GROUP_ALL];
+                return (string) $data[CustomerGroupService::CUST_GROUP_ALL];
             }
             return serialize($data);
         } else {
@@ -123,16 +123,10 @@ class Minsaleqty
             return false;
         }
         unset($value['__empty']);
-        foreach ($value as $_id => $row) {
-            if (!is_array(
-                $row
-            ) || !array_key_exists(
-                'customer_group_id',
-                $row
-            ) || !array_key_exists(
-                'min_sale_qty',
-                $row
-            )
+        foreach ($value as $row) {
+            if (!is_array($row)
+                || !array_key_exists('customer_group_id', $row)
+                || !array_key_exists('min_sale_qty', $row)
             ) {
                 return false;
             }
@@ -150,8 +144,8 @@ class Minsaleqty
     {
         $result = array();
         foreach ($value as $groupId => $qty) {
-            $_id = $this->mathRandom->getUniqueHash('_');
-            $result[$_id] = array('customer_group_id' => $groupId, 'min_sale_qty' => $this->_fixQty($qty));
+            $resultId = $this->mathRandom->getUniqueHash('_');
+            $result[$resultId] = array('customer_group_id' => $groupId, 'min_sale_qty' => $this->_fixQty($qty));
         }
         return $result;
     }
@@ -166,16 +160,10 @@ class Minsaleqty
     {
         $result = array();
         unset($value['__empty']);
-        foreach ($value as $_id => $row) {
-            if (!is_array(
-                $row
-            ) || !array_key_exists(
-                'customer_group_id',
-                $row
-            ) || !array_key_exists(
-                'min_sale_qty',
-                $row
-            )
+        foreach ($value as $row) {
+            if (!is_array($row)
+                || !array_key_exists('customer_group_id', $row)
+                || !array_key_exists('min_sale_qty', $row)
             ) {
                 continue;
             }
@@ -209,7 +197,7 @@ class Minsaleqty
             if ($groupId == $customerGroupId) {
                 $result = $qty;
                 break;
-            } else if ($groupId == CustomerGroupService::CUST_GROUP_ALL) {
+            } elseif ($groupId == CustomerGroupService::CUST_GROUP_ALL) {
                 $result = $qty;
             }
         }
diff --git a/app/code/Magento/CatalogInventory/Model/Config/Backend/Managestock.php b/app/code/Magento/CatalogInventory/Model/Config/Backend/Managestock.php
index 044c95ea187..ee210d5a1ae 100644
--- a/app/code/Magento/CatalogInventory/Model/Config/Backend/Managestock.php
+++ b/app/code/Magento/CatalogInventory/Model/Config/Backend/Managestock.php
@@ -66,12 +66,7 @@ class Managestock extends \Magento\Framework\App\Config\Value
      */
     protected function _afterSave()
     {
-        $oldValue = $this->_config->getValue(
-            \Magento\CatalogSearch\Model\Fulltext::XML_PATH_CATALOG_SEARCH_TYPE,
-            $this->getScope(),
-            $this->getScopeId()
-        );
-        if ($this->getValue() != $oldValue) {
+        if ($this->isValueChanged()) {
             $this->_stockStatus->rebuild();
         }
 
diff --git a/app/code/Magento/CatalogInventory/Model/Indexer/Stock.php b/app/code/Magento/CatalogInventory/Model/Indexer/Stock.php
index 5a9af011cdf..51d24b5e6d5 100644
--- a/app/code/Magento/CatalogInventory/Model/Indexer/Stock.php
+++ b/app/code/Magento/CatalogInventory/Model/Indexer/Stock.php
@@ -26,7 +26,6 @@ namespace Magento\CatalogInventory\Model\Indexer;
 /**
  * CatalogInventory Stock Status Indexer Model
  *
- * @method \Magento\CatalogInventory\Model\Resource\Indexer\Stock getResource()
  * @method int getProductId()
  * @method \Magento\CatalogInventory\Model\Indexer\Stock setProductId(int $value)
  * @method int getWebsiteId()
@@ -37,8 +36,6 @@ namespace Magento\CatalogInventory\Model\Indexer;
  * @method \Magento\CatalogInventory\Model\Indexer\Stock setQty(float $value)
  * @method int getStockStatus()
  * @method \Magento\CatalogInventory\Model\Indexer\Stock setStockStatus(int $value)
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
 class Stock extends \Magento\Index\Model\Indexer\AbstractIndexer
 {
@@ -212,11 +209,9 @@ class Stock extends \Magento\Index\Model\Indexer\AbstractIndexer
             case \Magento\CatalogInventory\Model\Stock\Item::ENTITY:
                 $this->_registerCatalogInventoryStockItemEvent($event);
                 break;
-
             case \Magento\Catalog\Model\Product::ENTITY:
                 $this->_registerCatalogProductEvent($event);
                 break;
-
             case \Magento\Store\Model\Store::ENTITY:
             case \Magento\Store\Model\Group::ENTITY:
             case \Magento\Framework\App\Config\ValueInterface::ENTITY:
@@ -227,14 +222,13 @@ class Stock extends \Magento\Index\Model\Indexer\AbstractIndexer
                 if ($event->getEntity() == \Magento\Framework\App\Config\ValueInterface::ENTITY) {
                     $configData = $event->getDataObject();
                     if ($configData->getPath() == \Magento\CatalogInventory\Helper\Data::XML_PATH_SHOW_OUT_OF_STOCK) {
-                        $this->_indexer->getProcessByCode(
-                            'catalog_product_attribute'
-                        )->changeStatus(
-                            \Magento\Index\Model\Process::STATUS_REQUIRE_REINDEX
-                        );
+                        $this->_indexer->getProcessByCode('catalog_product_attribute')
+                            ->changeStatus(\Magento\Index\Model\Process::STATUS_REQUIRE_REINDEX);
                     }
                 }
                 break;
+            default:
+                break;
         }
     }
 
@@ -256,10 +250,11 @@ class Stock extends \Magento\Index\Model\Indexer\AbstractIndexer
             case \Magento\Index\Model\Event::TYPE_MASS_ACTION:
                 $this->_registerCatalogProductMassActionEvent($event);
                 break;
-
             case \Magento\Index\Model\Event::TYPE_DELETE:
                 $this->_registerCatalogProductDeleteEvent($event);
                 break;
+            default:
+                break;
         }
     }
 
@@ -275,6 +270,8 @@ class Stock extends \Magento\Index\Model\Indexer\AbstractIndexer
             case \Magento\Index\Model\Event::TYPE_SAVE:
                 $this->_registerStockItemSaveEvent($event);
                 break;
+            default:
+                break;
         }
     }
 
@@ -294,7 +291,7 @@ class Stock extends \Magento\Index\Model\Indexer\AbstractIndexer
 
         // Saving stock item without product object
         // Register re-index price process if products out of stock hidden on Front-end
-        if (!$this->_catalogInventoryData->isShowOutOfStock() && !$object->getProduct()) {
+        if (!$this->_catalogInventoryData->isShowOutOfStock() /**&& !$object->getProduct() */) {
             $massObject = new \Magento\Framework\Object();
             $massObject->setAttributesData(array('force_reindex_required' => 1));
             $massObject->setProductIds(array($object->getProductId()));
diff --git a/app/code/Magento/CatalogInventory/Model/Observer.php b/app/code/Magento/CatalogInventory/Model/Observer.php
index 02f0d619bf4..18a9c826bc1 100644
--- a/app/code/Magento/CatalogInventory/Model/Observer.php
+++ b/app/code/Magento/CatalogInventory/Model/Observer.php
@@ -22,15 +22,15 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-/**
- * Catalog inventory module observer
- */
 namespace Magento\CatalogInventory\Model;
 
 use Magento\CatalogInventory\Model\Stock\Item;
 use Magento\Framework\Event\Observer as EventObserver;
 use Magento\Sales\Model\Quote\Item as QuoteItem;
 
+/**
+ * Catalog inventory module observer
+ */
 class Observer
 {
     /**
@@ -176,9 +176,9 @@ class Observer
     public function removeInventoryData($observer)
     {
         $product = $observer->getEvent()->getProduct();
-        if ($product instanceof \Magento\Catalog\Model\Product && $product->getId() && isset(
-            $this->_stockItemsArray[$product->getId()]
-        )
+        if ($product instanceof \Magento\Catalog\Model\Product
+            && $product->getId()
+            && isset($this->_stockItemsArray[$product->getId()])
         ) {
             unset($this->_stockItemsArray[$product->getId()]);
         }
@@ -186,7 +186,7 @@ class Observer
     }
 
     /**
-     * Add information about producs stock status to collection
+     * Add information about product stock status to collection
      * Used in for product collection after load
      *
      * @param EventObserver $observer
@@ -251,75 +251,51 @@ class Observer
      */
     protected function _prepareItemForSave($item, $product)
     {
-        $item->addData(
-            $product->getStockData()
-        )->setProduct(
-            $product
-        )->setProductId(
-            $product->getId()
-        )->setStockId(
-            $item->getStockId()
-        );
-        if (!is_null(
-            $product->getData('stock_data/min_qty')
-        ) && is_null(
-            $product->getData('stock_data/use_config_min_qty')
-        )
-        ) {
-            $item->setData('use_config_min_qty', false);
-        }
-        if (!is_null(
-            $product->getData('stock_data/min_sale_qty')
-        ) && is_null(
-            $product->getData('stock_data/use_config_min_sale_qty')
-        )
-        ) {
-            $item->setData('use_config_min_sale_qty', false);
-        }
-        if (!is_null(
-            $product->getData('stock_data/max_sale_qty')
-        ) && is_null(
-            $product->getData('stock_data/use_config_max_sale_qty')
-        )
-        ) {
-            $item->setData('use_config_max_sale_qty', false);
-        }
-        if (!is_null(
-            $product->getData('stock_data/backorders')
-        ) && is_null(
-            $product->getData('stock_data/use_config_backorders')
-        )
-        ) {
-            $item->setData('use_config_backorders', false);
-        }
-        if (!is_null(
-            $product->getData('stock_data/notify_stock_qty')
-        ) && is_null(
-            $product->getData('stock_data/use_config_notify_stock_qty')
-        )
-        ) {
-            $item->setData('use_config_notify_stock_qty', false);
+        $item->addData($product->getStockData())
+            ->setProduct($product)
+            ->setProductId($product->getId())
+            ->setStockId($item->getStockId());
+
+        $paramListToCheck = [
+            'use_config_min_qty' => [
+                'item' => 'stock_data/min_qty',
+                'config' => 'stock_data/use_config_min_qty',
+            ],
+            'use_config_min_sale_qty' => [
+                'item' => 'stock_data/min_sale_qty',
+                'config' => 'stock_data/use_config_min_sale_qty',
+            ],
+            'use_config_max_sale_qty' => [
+                'item' => 'stock_data/max_sale_qty',
+                'config' => 'stock_data/use_config_max_sale_qty',
+            ],
+            'use_config_backorders' => [
+                'item' => 'stock_data/backorders',
+                'config' => 'stock_data/use_config_backorders',
+            ],
+            'use_config_notify_stock_qty' => [
+                'item' => 'stock_data/notify_stock_qty',
+                'config' => 'stock_data/use_config_notify_stock_qty',
+            ],
+            'use_config_enable_qty_inc' => [
+                'item' => 'stock_data/enable_qty_increments',
+                'config' => 'stock_data/use_config_enable_qty_inc',
+            ],
+            'use_config_qty_increments' => [
+                'item' => 'stock_data/qty_increments',
+                'config' => 'stock_data/use_config_qty_increments',
+            ],
+        ];
+        foreach ($paramListToCheck as $dataKey => $configPath) {
+            if (null !== $product->getData($configPath['item']) && null === $product->getData($configPath['config'])) {
+                $item->setData($dataKey, false);
+            }
         }
+
         $originalQty = $product->getData('stock_data/original_inventory_qty');
         if (strlen($originalQty) > 0) {
             $item->setQtyCorrection($item->getQty() - $originalQty);
         }
-        if (!is_null(
-            $product->getData('stock_data/enable_qty_increments')
-        ) && is_null(
-            $product->getData('stock_data/use_config_enable_qty_inc')
-        )
-        ) {
-            $item->setData('use_config_enable_qty_inc', false);
-        }
-        if (!is_null(
-            $product->getData('stock_data/qty_increments')
-        ) && is_null(
-            $product->getData('stock_data/use_config_qty_increments')
-        )
-        ) {
-            $item->setData('use_config_qty_increments', false);
-        }
         return $this;
     }
 
@@ -346,7 +322,7 @@ class Observer
      * Also called after every successful order placement to ensure subtraction of inventory
      *
      * @param EventObserver $observer
-     * @return $this|void
+     * @return $this
      */
     public function subtractQuoteInventory(EventObserver $observer)
     {
@@ -355,7 +331,7 @@ class Observer
         // Maybe we've already processed this quote in some event during order placement
         // e.g. call in event 'sales_model_service_quote_submit_before' and later in 'checkout_submit_all_after'
         if ($quote->getInventoryProcessed()) {
-            return;
+            return $this;
         }
         $items = $this->_getProductsQty($quote->getAllItems());
 
@@ -538,8 +514,8 @@ class Observer
         $children = $item->getChildrenItems();
         $qty = $item->getQtyOrdered() - max($item->getQtyShipped(), $item->getQtyInvoiced()) - $item->getQtyCanceled();
 
-        if ($item->getId() && ($productId = $item->getProductId()) && empty($children) && $qty) {
-            $this->_stock->backItemQty($productId, $qty);
+        if ($item->getId() && $item->getProductId() && empty($children) && $qty) {
+            $this->_stock->backItemQty($item->getProductId(), $qty);
         }
 
         return $this;
@@ -548,10 +524,9 @@ class Observer
     /**
      * Update items stock status and low stock date.
      *
-     * @param EventObserver $observer
      * @return $this
      */
-    public function updateItemsStockUponConfigChange($observer)
+    public function updateItemsStockUponConfigChange()
     {
         $this->_resourceStock->updateSetOutOfStock();
         $this->_resourceStock->updateSetInStock();
@@ -628,10 +603,9 @@ class Observer
     /**
      * Reindex all events of product-massAction type
      *
-     * @param EventObserver $observer
      * @return void
      */
-    public function reindexProductsMassAction($observer)
+    public function reindexProductsMassAction()
     {
         $this->_indexer->indexEvents(
             \Magento\Catalog\Model\Product::ENTITY,
diff --git a/app/code/Magento/CatalogInventory/Model/Product/CopyConstructor/CatalogInventory.php b/app/code/Magento/CatalogInventory/Model/Product/CopyConstructor/CatalogInventory.php
index f90095b1c28..f3c2260206e 100644
--- a/app/code/Magento/CatalogInventory/Model/Product/CopyConstructor/CatalogInventory.php
+++ b/app/code/Magento/CatalogInventory/Model/Product/CopyConstructor/CatalogInventory.php
@@ -43,7 +43,8 @@ class CatalogInventory implements \Magento\Catalog\Model\Product\CopyConstructor
             'use_config_notify_stock_qty' => 1
         );
         /** @var \Magento\CatalogInventory\Model\Stock\Item $currentStockItem */
-        if ($currentStockItem = $product->getStockItem()) {
+        $currentStockItem = $product->getStockItem();
+        if ($currentStockItem) {
             $stockData += array(
                 'use_config_enable_qty_inc' => $currentStockItem->getData('use_config_enable_qty_inc'),
                 'enable_qty_increments' => $currentStockItem->getData('enable_qty_increments'),
diff --git a/app/code/Magento/CatalogInventory/Model/Resource/Indexer/Stock.php b/app/code/Magento/CatalogInventory/Model/Resource/Indexer/Stock.php
index 96c2f0c86f4..4b1659ee7ef 100644
--- a/app/code/Magento/CatalogInventory/Model/Resource/Indexer/Stock.php
+++ b/app/code/Magento/CatalogInventory/Model/Resource/Indexer/Stock.php
@@ -22,14 +22,11 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
+namespace Magento\CatalogInventory\Model\Resource\Indexer;
 
 /**
  * CatalogInventory Stock Status Indexer Resource Model
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
-namespace Magento\CatalogInventory\Model\Resource\Indexer;
-
 class Stock extends \Magento\Catalog\Model\Resource\Product\Indexer\AbstractIndexer
 {
     /**
@@ -117,13 +114,8 @@ class Stock extends \Magento\Catalog\Model\Resource\Product\Indexer\AbstractInde
         }
 
         // retrieve product types by processIds
-        $select = $adapter->select()->from(
-            $this->getTable('catalog_product_entity'),
-            array('entity_id', 'type_id')
-        )->where(
-            'entity_id IN(?)',
-            $processIds
-        );
+        $select = $adapter->select()->from($this->getTable('catalog_product_entity'), array('entity_id', 'type_id'))
+            ->where('entity_id IN(?)', $processIds);
         $pairs = $adapter->fetchPairs($select);
 
         $byType = array();
@@ -209,21 +201,11 @@ class Stock extends \Magento\Catalog\Model\Resource\Product\Indexer\AbstractInde
         }
 
         // calculate relations
-        $select = $adapter->select()->from(
-            $this->getTable('catalog_product_relation'),
-            'COUNT(DISTINCT parent_id)'
-        )->where(
-            'child_id IN(?)',
-            $processIds
-        );
+        $select = $adapter->select()->from($this->getTable('catalog_product_relation'), 'COUNT(DISTINCT parent_id)')
+            ->where('child_id IN(?)', $processIds);
         $aCount = $adapter->fetchOne($select);
-        $select = $adapter->select()->from(
-            $this->getTable('catalog_product_relation'),
-            'COUNT(DISTINCT child_id)'
-        )->where(
-            'parent_id IN(?)',
-            $processIds
-        );
+        $select = $adapter->select()->from($this->getTable('catalog_product_relation'), 'COUNT(DISTINCT child_id)')
+            ->where('parent_id IN(?)', $processIds);
         $bCount = $adapter->fetchOne($select);
 
         // if affected with relations more 30% of all products - run reindex all products
@@ -239,13 +221,8 @@ class Stock extends \Magento\Catalog\Model\Resource\Product\Indexer\AbstractInde
         }
 
         // retrieve products types
-        $select = $adapter->select()->from(
-            $this->getTable('catalog_product_entity'),
-            array('entity_id', 'type_id')
-        )->where(
-            'entity_id IN(?)',
-            $processIds
-        );
+        $select = $adapter->select()->from($this->getTable('catalog_product_entity'), array('entity_id', 'type_id'))
+            ->where('entity_id IN(?)', $processIds);
         $query = $select->query(\Zend_Db::FETCH_ASSOC);
         $byType = array();
         while ($row = $query->fetch()) {
@@ -306,14 +283,9 @@ class Stock extends \Magento\Catalog\Model\Resource\Product\Indexer\AbstractInde
             foreach ($this->_productType->getTypesByPriority() as $typeId => $typeInfo) {
                 $indexerClassName = isset($typeInfo['stock_indexer']) ? $typeInfo['stock_indexer'] : '';
 
-                $indexer = $this->_indexerFactory->create(
-                    $indexerClassName
-                )->setTypeId(
-                    $typeId
-                )->setIsComposite(
-                    !empty($typeInfo['composite'])
-                );
-
+                $indexer = $this->_indexerFactory->create($indexerClassName)
+                    ->setTypeId($typeId)
+                    ->setIsComposite(!empty($typeInfo['composite']));
                 $this->_indexers[$typeId] = $indexer;
             }
         }
@@ -346,16 +318,9 @@ class Stock extends \Magento\Catalog\Model\Resource\Product\Indexer\AbstractInde
     public function getProductParentsByChild($childId)
     {
         $write = $this->_getWriteAdapter();
-        $select = $write->select()->from(
-            array('l' => $this->getTable('catalog_product_relation')),
-            array('parent_id')
-        )->join(
-            array('e' => $this->getTable('catalog_product_entity')),
-            'l.parent_id=e.entity_id',
-            array('e.type_id')
-        )->where(
-            'l.child_id = :child_id'
-        );
+        $select = $write->select()->from(['l' => $this->getTable('catalog_product_relation')], ['parent_id'])
+            ->join(['e' => $this->getTable('catalog_product_entity')], 'l.parent_id=e.entity_id', ['e.type_id'])
+            ->where('l.child_id = :child_id');
         return $write->fetchPairs($select, array(':child_id' => $childId));
     }
 
diff --git a/app/code/Magento/CatalogInventory/Model/Resource/Indexer/Stock/DefaultStock.php b/app/code/Magento/CatalogInventory/Model/Resource/Indexer/Stock/DefaultStock.php
index ab60bd0f6c9..5f1a72f4825 100644
--- a/app/code/Magento/CatalogInventory/Model/Resource/Indexer/Stock/DefaultStock.php
+++ b/app/code/Magento/CatalogInventory/Model/Resource/Indexer/Stock/DefaultStock.php
@@ -22,14 +22,11 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
+namespace Magento\CatalogInventory\Model\Resource\Indexer\Stock;
 
 /**
  * CatalogInventory Default Stock Status Indexer Resource Model
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
-namespace Magento\CatalogInventory\Model\Resource\Indexer\Stock;
-
 class DefaultStock extends \Magento\Catalog\Model\Resource\Product\Indexer\AbstractIndexer implements StockInterface
 {
     /**
@@ -145,7 +142,7 @@ class DefaultStock extends \Magento\Catalog\Model\Resource\Product\Indexer\Abstr
      */
     public function setIsComposite($flag)
     {
-        $this->_isComposite = (bool)$flag;
+        $this->_isComposite = (bool) $flag;
         return $this;
     }
 
@@ -189,9 +186,7 @@ class DefaultStock extends \Magento\Catalog\Model\Resource\Product\Indexer\Abstr
         );
         $this->_addWebsiteJoinToSelect($select, true);
         $this->_addProductWebsiteJoinToSelect($select, 'cw.website_id', 'e.entity_id');
-        $select->columns(
-            'cw.website_id'
-        )->join(
+        $select->columns('cw.website_id')->join(
             array('cis' => $this->getTable('cataloginventory_stock')),
             '',
             array('stock_id')
@@ -199,14 +194,9 @@ class DefaultStock extends \Magento\Catalog\Model\Resource\Product\Indexer\Abstr
             array('cisi' => $this->getTable('cataloginventory_stock_item')),
             'cisi.stock_id = cis.stock_id AND cisi.product_id = e.entity_id',
             array()
-        )->columns(
-            array('qty' => $qtyExpr)
-        )->where(
-            'cw.website_id != 0'
-        )->where(
-            'e.type_id = ?',
-            $this->getTypeId()
-        );
+        )->columns(array('qty' => $qtyExpr))
+            ->where('cw.website_id != 0')
+            ->where('e.type_id = ?', $this->getTypeId());
 
         // add limitation of status
         $condition = $adapter->quoteInto('=?', \Magento\Catalog\Model\Product\Attribute\Source\Status::STATUS_ENABLED);
diff --git a/app/code/Magento/CatalogInventory/Model/Resource/Stock.php b/app/code/Magento/CatalogInventory/Model/Resource/Stock.php
index c5a4d612dd7..f2eac875267 100644
--- a/app/code/Magento/CatalogInventory/Model/Resource/Stock.php
+++ b/app/code/Magento/CatalogInventory/Model/Resource/Stock.php
@@ -22,12 +22,11 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
+namespace Magento\CatalogInventory\Model\Resource;
 
 /**
  * Stock resource model
  */
-namespace Magento\CatalogInventory\Model\Resource;
-
 class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
 {
     /**
@@ -80,11 +79,9 @@ class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
     protected $_stock;
 
     /**
-     * Catalog inventory data
-     *
-     * @var \Magento\CatalogInventory\Helper\Data
+     * @var \Magento\CatalogInventory\Service\V1\StockItem
      */
-    protected $_catalogInventoryData;
+    protected $stockItemService;
 
     /**
      * Core store config
@@ -106,23 +103,21 @@ class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
     protected $dateTime;
 
     /**
-     * Construct
-     * 
      * @param \Magento\Framework\App\Resource $resource
-     * @param \Magento\CatalogInventory\Helper\Data $catalogInventoryData
+     * @param \Magento\CatalogInventory\Service\V1\StockItem $stockItemService
      * @param \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig
      * @param \Magento\CatalogInventory\Model\StockFactory $stockFactory
      * @param \Magento\Framework\Stdlib\DateTime $dateTime
      */
     public function __construct(
         \Magento\Framework\App\Resource $resource,
-        \Magento\CatalogInventory\Helper\Data $catalogInventoryData,
+        \Magento\CatalogInventory\Service\V1\StockItem $stockItemService,
         \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig,
         \Magento\CatalogInventory\Model\StockFactory $stockFactory,
         \Magento\Framework\Stdlib\DateTime $dateTime
     ) {
         parent::__construct($resource);
-        $this->_catalogInventoryData = $catalogInventoryData;
+        $this->stockItemService = $stockItemService;
         $this->_scopeConfig = $scopeConfig;
         $this->_stockFactory = $stockFactory;
         $this->dateTime = $dateTime;
@@ -148,17 +143,10 @@ class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
     public function lockProductItems($stock, $productIds)
     {
         $itemTable = $this->getTable('cataloginventory_stock_item');
-        $select = $this->_getWriteAdapter()->select()->from(
-            $itemTable
-        )->where(
-            'stock_id=?',
-            $stock->getId()
-        )->where(
-            'product_id IN(?)',
-            $productIds
-        )->forUpdate(
-            true
-        );
+        $select = $this->_getWriteAdapter()->select()->from($itemTable)
+            ->where('stock_id=?', $stock->getId())
+            ->where('product_id IN(?)', $productIds)
+            ->forUpdate(true);
         /**
          * We use write adapter for resolving problems with replication
          */
@@ -181,21 +169,11 @@ class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
         }
         $itemTable = $this->getTable('cataloginventory_stock_item');
         $productTable = $this->getTable('catalog_product_entity');
-        $select = $this->_getWriteAdapter()->select()->from(
-            array('si' => $itemTable)
-        )->join(
-            array('p' => $productTable),
-            'p.entity_id=si.product_id',
-            array('type_id')
-        )->where(
-            'stock_id=?',
-            $stock->getId()
-        )->where(
-            'product_id IN(?)',
-            $productIds
-        )->forUpdate(
-            $lockRows
-        );
+        $select = $this->_getWriteAdapter()->select()->from(array('si' => $itemTable))
+            ->join(array('p' => $productTable), 'p.entity_id=si.product_id', array('type_id'))
+            ->where('stock_id=?', $stock->getId())
+            ->where('product_id IN(?)', $productIds)
+            ->forUpdate($lockRows);
         return $this->_getWriteAdapter()->fetchAll($select);
     }
 
@@ -222,7 +200,6 @@ class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
         }
 
         $value = $adapter->getCaseSql('product_id', $conditions, 'qty');
-
         $where = array('product_id IN (?)' => array_keys($productQtys), 'stock_id = ?' => $stock->getId());
 
         $adapter->beginTransaction();
@@ -281,7 +258,7 @@ class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
             );
 
             foreach ($configMap as $field => $const) {
-                $this->{$field} = (int)$this->_scopeConfig->getValue(
+                $this->{$field} = (int) $this->_scopeConfig->getValue(
                     $const,
                     \Magento\Store\Model\ScopeInterface::SCOPE_STORE
                 );
@@ -289,7 +266,7 @@ class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
 
             $this->_isConfig = true;
             $this->_stock = $this->_stockFactory->create();
-            $this->_configTypeIds = array_keys($this->_catalogInventoryData->getIsQtyTypeIds(true));
+            $this->_configTypeIds = array_keys($this->stockItemService->getIsQtyTypeIds(true));
         }
     }
 
@@ -304,13 +281,8 @@ class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
         $adapter = $this->_getWriteAdapter();
         $values = array('is_in_stock' => 0, 'stock_status_changed_auto' => 1);
 
-        $select = $adapter->select()->from(
-            $this->getTable('catalog_product_entity'),
-            'entity_id'
-        )->where(
-            'type_id IN(?)',
-            $this->_configTypeIds
-        );
+        $select = $adapter->select()->from($this->getTable('catalog_product_entity'), 'entity_id')
+            ->where('type_id IN(?)', $this->_configTypeIds);
 
         $where = sprintf(
             'stock_id = %1$d' .
@@ -341,13 +313,8 @@ class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
         $adapter = $this->_getWriteAdapter();
         $values = array('is_in_stock' => 1);
 
-        $select = $adapter->select()->from(
-            $this->getTable('catalog_product_entity'),
-            'entity_id'
-        )->where(
-            'type_id IN(?)',
-            $this->_configTypeIds
-        );
+        $select = $adapter->select()->from($this->getTable('catalog_product_entity'), 'entity_id')
+            ->where('type_id IN(?)', $this->_configTypeIds);
 
         $where = sprintf(
             'stock_id = %1$d' .
@@ -384,13 +351,8 @@ class Stock extends \Magento\Framework\Model\Resource\Db\AbstractDb
 
         $value = array('low_stock_date' => new \Zend_Db_Expr($conditionalDate));
 
-        $select = $adapter->select()->from(
-            $this->getTable('catalog_product_entity'),
-            'entity_id'
-        )->where(
-            'type_id IN(?)',
-            $this->_configTypeIds
-        );
+        $select = $adapter->select()->from($this->getTable('catalog_product_entity'), 'entity_id')
+            ->where('type_id IN(?)', $this->_configTypeIds);
 
         $where = sprintf(
             'stock_id = %1$d' .
diff --git a/app/code/Magento/CatalogInventory/Model/Resource/Stock/Item.php b/app/code/Magento/CatalogInventory/Model/Resource/Stock/Item.php
index eb05ba2213a..49bef032311 100644
--- a/app/code/Magento/CatalogInventory/Model/Resource/Stock/Item.php
+++ b/app/code/Magento/CatalogInventory/Model/Resource/Stock/Item.php
@@ -22,14 +22,11 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
+namespace Magento\CatalogInventory\Model\Resource\Stock;
 
 /**
  * Stock item resource model
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
-namespace Magento\CatalogInventory\Model\Resource\Stock;
-
 class Item extends \Magento\Framework\Model\Resource\Db\AbstractDb
 {
     /**
@@ -89,15 +86,8 @@ class Item extends \Magento\Framework\Model\Resource\Db\AbstractDb
      */
     protected function _getLoadSelect($field, $value, $object)
     {
-        $select = parent::_getLoadSelect(
-            $field,
-            $value,
-            $object
-        )->join(
-            array('p' => $this->getTable('catalog_product_entity')),
-            'product_id=p.entity_id',
-            array('type_id')
-        );
+        $select = parent::_getLoadSelect($field, $value, $object)
+            ->join(array('p' => $this->getTable('catalog_product_entity')), 'product_id=p.entity_id', array('type_id'));
         return $select;
     }
 
diff --git a/app/code/Magento/CatalogInventory/Model/Resource/Stock/Status.php b/app/code/Magento/CatalogInventory/Model/Resource/Stock/Status.php
index 637ce2bb119..466d1020ffa 100644
--- a/app/code/Magento/CatalogInventory/Model/Resource/Stock/Status.php
+++ b/app/code/Magento/CatalogInventory/Model/Resource/Stock/Status.php
@@ -23,6 +23,8 @@
  */
 namespace Magento\CatalogInventory\Model\Resource\Stock;
 
+use Magento\CatalogInventory\Model\Stock;
+
 /**
  * CatalogInventory Stock Status per website Resource Model
  */
@@ -79,7 +81,7 @@ class Status extends \Magento\Framework\Model\Resource\Db\AbstractDb
     /**
      * Save Product Status per website
      *
-     * @param \Magento\CatalogInventory\Model\Stock\Status $object
+     * @param Stock\Status $object
      * @param int $productId
      * @param int $status
      * @param float|int $qty
@@ -88,7 +90,7 @@ class Status extends \Magento\Framework\Model\Resource\Db\AbstractDb
      * @return $this
      */
     public function saveProductStatus(
-        \Magento\CatalogInventory\Model\Stock\Status $object,
+        Stock\Status $object,
         $productId,
         $status,
         $qty = 0,
@@ -140,7 +142,7 @@ class Status extends \Magento\Framework\Model\Resource\Db\AbstractDb
      * @param int $stockId
      * @return array
      */
-    public function getProductStockStatus($productIds, $websiteId, $stockId = 1)
+    public function getProductStockStatus($productIds, $websiteId, $stockId = Stock::DEFAULT_STOCK_ID)
     {
         if (!is_array($productIds)) {
             $productIds = array($productIds);
@@ -162,38 +164,6 @@ class Status extends \Magento\Framework\Model\Resource\Db\AbstractDb
         return $this->_getReadAdapter()->fetchPairs($select);
     }
 
-    /**
-     * Retrieve product(s) data array
-     *
-     * @param int|array $productIds
-     * @param int $websiteId
-     * @param int $stockId
-     * @return array
-     */
-    public function getProductData($productIds, $websiteId, $stockId = 1)
-    {
-        if (!is_array($productIds)) {
-            $productIds = array($productIds);
-        }
-
-        $result = array();
-
-        $select = $this->_getReadAdapter()->select()->from(
-            $this->getMainTable()
-        )->where(
-            'product_id IN(?)',
-            $productIds
-        )->where(
-            'stock_id=?',
-            (int)$stockId
-        )->where(
-            'website_id=?',
-            (int)$websiteId
-        );
-        $result = $this->_getReadAdapter()->fetchAssoc($select);
-        return $result;
-    }
-
     /**
      * Retrieve websites and default stores
      * Return array as key website_id, value store_id
@@ -286,7 +256,7 @@ class Status extends \Magento\Framework\Model\Resource\Db\AbstractDb
             "ciss.product_id = {$entityField} AND ciss.website_id = {$websiteField}",
             array()
         );
-        $select->where('ciss.stock_status = ?', \Magento\CatalogInventory\Model\Stock\Status::STATUS_IN_STOCK);
+        $select->where('ciss.stock_status = ?', Stock\Status::STATUS_IN_STOCK);
 
         return $this;
     }
@@ -307,7 +277,7 @@ class Status extends \Magento\Framework\Model\Resource\Db\AbstractDb
 
         $joinCondition .= $this->_getReadAdapter()->quoteInto(
             ' AND stock_status_index.stock_id = ?',
-            \Magento\CatalogInventory\Model\Stock::DEFAULT_STOCK_ID
+            Stock::DEFAULT_STOCK_ID
         );
 
         $collection->getSelect()->join(
@@ -316,7 +286,7 @@ class Status extends \Magento\Framework\Model\Resource\Db\AbstractDb
             array()
         )->where(
             'stock_status_index.stock_status=?',
-            \Magento\CatalogInventory\Model\Stock\Status::STATUS_IN_STOCK
+            Stock\Status::STATUS_IN_STOCK
         );
         return $this;
     }
diff --git a/app/code/Magento/CatalogInventory/Model/Source/Backorders.php b/app/code/Magento/CatalogInventory/Model/Source/Backorders.php
index df0213a3864..a89f368bc34 100644
--- a/app/code/Magento/CatalogInventory/Model/Source/Backorders.php
+++ b/app/code/Magento/CatalogInventory/Model/Source/Backorders.php
@@ -23,6 +23,9 @@
  */
 namespace Magento\CatalogInventory\Model\Source;
 
+/**
+ * Back orders source class
+ */
 class Backorders implements \Magento\Framework\Option\ArrayInterface
 {
     /**
diff --git a/app/code/Magento/CatalogInventory/Model/Source/Stock.php b/app/code/Magento/CatalogInventory/Model/Source/Stock.php
index b193e4ce5dc..e91de41890d 100644
--- a/app/code/Magento/CatalogInventory/Model/Source/Stock.php
+++ b/app/code/Magento/CatalogInventory/Model/Source/Stock.php
@@ -22,14 +22,11 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
+namespace Magento\CatalogInventory\Model\Source;
 
 /**
  * CatalogInventory Stock source model
- *
- * @author     Magento Core Team <core@magentocommerce.com>
  */
-namespace Magento\CatalogInventory\Model\Source;
-
 class Stock implements \Magento\Framework\Option\ArrayInterface
 {
     /**
diff --git a/app/code/Magento/CatalogInventory/Model/Stock.php b/app/code/Magento/CatalogInventory/Model/Stock.php
index 01a2fc2ba32..a832a2952a2 100644
--- a/app/code/Magento/CatalogInventory/Model/Stock.php
+++ b/app/code/Magento/CatalogInventory/Model/Stock.php
@@ -28,8 +28,6 @@ use Magento\CatalogInventory\Model\Stock\Item;
 /**
  * Stock model
  *
- * @method \Magento\CatalogInventory\Model\Resource\Stock _getResource()
- * @method \Magento\CatalogInventory\Model\Resource\Stock getResource()
  * @method string getStockName()
  * @method \Magento\CatalogInventory\Model\Stock setStockName(string $value)
  */
@@ -45,14 +43,15 @@ class Stock extends \Magento\Framework\Model\AbstractModel
 
     const STOCK_IN_STOCK = 1;
 
+    /**
+     * Default stock id
+     */
     const DEFAULT_STOCK_ID = 1;
 
     /**
-     * Catalog inventory data
-     *
-     * @var \Magento\CatalogInventory\Helper\Data
+     * @var \Magento\CatalogInventory\Service\V1\StockItem
      */
-    protected $_catalogInventoryData;
+    protected $stockItemService;
 
     /**
      * Store model manager
@@ -76,10 +75,10 @@ class Stock extends \Magento\Framework\Model\AbstractModel
     /**
      * @param \Magento\Framework\Model\Context $context
      * @param \Magento\Framework\Registry $registry
-     * @param \Magento\CatalogInventory\Model\Resource\Stock\Item\CollectionFactory $collectionFactory
-     * @param \Magento\CatalogInventory\Helper\Data $catalogInventoryData
+     * @param Resource\Stock\Item\CollectionFactory $collectionFactory
+     * @param \Magento\CatalogInventory\Service\V1\StockItem $stockItemService
      * @param \Magento\Store\Model\StoreManagerInterface $storeManager
-     * @param \Magento\CatalogInventory\Model\Stock\ItemFactory $stockItemFactory
+     * @param Stock\ItemFactory $stockItemFactory
      * @param \Magento\Framework\Model\Resource\AbstractResource $resource
      * @param \Magento\Framework\Data\Collection\Db $resourceCollection
      * @param array $data
@@ -88,7 +87,7 @@ class Stock extends \Magento\Framework\Model\AbstractModel
         \Magento\Framework\Model\Context $context,
         \Magento\Framework\Registry $registry,
         \Magento\CatalogInventory\Model\Resource\Stock\Item\CollectionFactory $collectionFactory,
-        \Magento\CatalogInventory\Helper\Data $catalogInventoryData,
+        \Magento\CatalogInventory\Service\V1\StockItem $stockItemService,
         \Magento\Store\Model\StoreManagerInterface $storeManager,
         \Magento\CatalogInventory\Model\Stock\ItemFactory $stockItemFactory,
         \Magento\Framework\Model\Resource\AbstractResource $resource = null,
@@ -98,7 +97,7 @@ class Stock extends \Magento\Framework\Model\AbstractModel
         parent::__construct($context, $registry, $resource, $resourceCollection, $data);
 
         $this->_collectionFactory = $collectionFactory;
-        $this->_catalogInventoryData = $catalogInventoryData;
+        $this->stockItemService = $stockItemService;
         $this->_storeManager = $storeManager;
         $this->_stockItemFactory = $stockItemFactory;
     }
@@ -172,7 +171,7 @@ class Stock extends \Magento\Framework\Model\AbstractModel
                 $stockItem = $item['item'];
             }
             $canSubtractQty = $stockItem->getId() && $stockItem->canSubtractQty();
-            if ($canSubtractQty && $this->_catalogInventoryData->isQty($stockItem->getTypeId())) {
+            if ($canSubtractQty && $this->stockItemService->isQty($stockItem->getTypeId())) {
                 $qtys[$productId] = $item['qty'];
             }
         }
@@ -234,20 +233,21 @@ class Stock extends \Magento\Framework\Model\AbstractModel
     public function registerItemSale(\Magento\Framework\Object $item)
     {
         $productId = $item->getProductId();
-        if ($productId) {
-            /** @var Item $stockItem */
-            $stockItem = $this->_stockItemFactory->create()->loadByProduct($productId);
-            if ($this->_catalogInventoryData->isQty($stockItem->getTypeId())) {
-                if ($item->getStoreId()) {
-                    $stockItem->setStoreId($item->getStoreId());
-                }
-                if ($stockItem->checkQty($item->getQtyOrdered())) {
-                    $stockItem->subtractQty($item->getQtyOrdered());
-                    $stockItem->save();
-                }
+        if (!$productId) {
+            throw new \Magento\Framework\Model\Exception(
+                __('We cannot specify a product identifier for the order item.')
+            );
+        }
+        /** @var Item $stockItem */
+        $stockItem = $this->_stockItemFactory->create()->loadByProduct($productId);
+        if ($this->stockItemService->isQty($stockItem->getTypeId())) {
+            if ($item->getStoreId()) {
+                $stockItem->setStoreId($item->getStoreId());
+            }
+            if ($stockItem->checkQty($item->getQtyOrdered())) {
+                $stockItem->subtractQty($item->getQtyOrdered());
+                $stockItem->save();
             }
-        } else {
-            throw new \Magento\Framework\Model\Exception(__('We cannot specify a product identifier for the order item.'));
         }
         return $this;
     }
@@ -263,7 +263,7 @@ class Stock extends \Magento\Framework\Model\AbstractModel
     {
         /** @var Item $stockItem */
         $stockItem = $this->_stockItemFactory->create()->loadByProduct($productId);
-        if ($stockItem->getId() && $this->_catalogInventoryData->isQty($stockItem->getTypeId())) {
+        if ($stockItem->getId() && $this->stockItemService->isQty($stockItem->getTypeId())) {
             $stockItem->addQty($qty);
             if ($stockItem->getCanBackInStock() && $stockItem->getQty() > $stockItem->getMinQty()) {
                 $stockItem->setIsInStock(true)->setStockStatusChangedAutomaticallyFlag(true);
diff --git a/app/code/Magento/CatalogInventory/Model/Stock/Item.php b/app/code/Magento/CatalogInventory/Model/Stock/Item.php
index da5e39047ff..0bad5e7727a 100644
--- a/app/code/Magento/CatalogInventory/Model/Stock/Item.php
+++ b/app/code/Magento/CatalogInventory/Model/Stock/Item.php
@@ -28,8 +28,6 @@ use Magento\Catalog\Model\Product;
 /**
  * Catalog Inventory Stock Model
  *
- * @method \Magento\CatalogInventory\Model\Resource\Stock\Item _getResource()
- * @method \Magento\CatalogInventory\Model\Resource\Stock\Item getResource()
  * @method \Magento\CatalogInventory\Model\Stock\Item setProductId(int $value)
  * @method \Magento\CatalogInventory\Model\Stock\Item setStockId(int $value)
  * @method float getQty()
@@ -65,35 +63,72 @@ use Magento\Catalog\Model\Product;
  * @method int getUseConfigEnableQtyInc()
  * @method \Magento\CatalogInventory\Model\Stock\Item setUseConfigEnableQtyInc(int $value)
  * @method \Magento\CatalogInventory\Model\Stock\Item setEnableQtyIncrements(int $value)
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
 class Item extends \Magento\Framework\Model\AbstractModel
 {
+    /**
+     * Inventory options config path
+     */
     const XML_PATH_GLOBAL = 'cataloginventory/options/';
 
+    /**
+     * Subtract config path
+     */
     const XML_PATH_CAN_SUBTRACT = 'cataloginventory/options/can_subtract';
 
+    /**
+     * Back in stock config path
+     */
     const XML_PATH_CAN_BACK_IN_STOCK = 'cataloginventory/options/can_back_in_stock';
 
+    /**
+     * Item options config path
+     */
     const XML_PATH_ITEM = 'cataloginventory/item_options/';
 
+    /**
+     * Max qty config path
+     */
     const XML_PATH_MIN_QTY = 'cataloginventory/item_options/min_qty';
 
+    /**
+     * Min sale qty config path
+     */
     const XML_PATH_MIN_SALE_QTY = 'cataloginventory/item_options/min_sale_qty';
 
+    /**
+     * Max sale qty config path
+     */
     const XML_PATH_MAX_SALE_QTY = 'cataloginventory/item_options/max_sale_qty';
 
+    /**
+     * Back orders config path
+     */
     const XML_PATH_BACKORDERS = 'cataloginventory/item_options/backorders';
 
+    /**
+     * Notify stock config path
+     */
     const XML_PATH_NOTIFY_STOCK_QTY = 'cataloginventory/item_options/notify_stock_qty';
 
+    /**
+     * Manage stock config path
+     */
     const XML_PATH_MANAGE_STOCK = 'cataloginventory/item_options/manage_stock';
 
+    /**
+     * Enable qty increments config path
+     */
     const XML_PATH_ENABLE_QTY_INCREMENTS = 'cataloginventory/item_options/enable_qty_increments';
 
+    /**
+     * Qty increments config path
+     */
     const XML_PATH_QTY_INCREMENTS = 'cataloginventory/item_options/qty_increments';
 
+    /**
+     * Stock item entity code
+     */
     const ENTITY = 'cataloginventory_stock_item';
 
     /**
@@ -122,19 +157,12 @@ class Item extends \Magento\Framework\Model\AbstractModel
      */
     protected $_eventObject = 'item';
 
-    /**
-     * Associated product instance
-     *
-     * @var Product
-     */
-    protected $_productInstance = null;
-
     /**
      * Customer group id
      *
      * @var int|null
      */
-    protected $_customerGroupId = null;
+    protected $_customerGroupId;
 
     /**
      * Whether index events should be processed immediately
@@ -144,18 +172,16 @@ class Item extends \Magento\Framework\Model\AbstractModel
     protected $_processIndexEvents = true;
 
     /**
-     * Catalog inventory minsaleqty
+     * Catalog inventory min sale qty
      *
      * @var \Magento\CatalogInventory\Helper\Minsaleqty
      */
     protected $_catalogInventoryMinsaleqty;
 
     /**
-     * Catalog inventory data
-     *
-     * @var \Magento\CatalogInventory\Helper\Data
+     * @var \Magento\CatalogInventory\Service\V1\StockItem
      */
-    protected $_catalogInventoryData;
+    protected $stockItemService;
 
     /**
      * Core store config
@@ -201,19 +227,25 @@ class Item extends \Magento\Framework\Model\AbstractModel
      */
     protected $_localeDate;
 
+    /**
+     * @var \Magento\Catalog\Model\ProductFactory
+     */
+    protected $productFactory;
+
     /**
      * @param \Magento\Framework\Model\Context $context
      * @param \Magento\Framework\Registry $registry
      * @param \Magento\Customer\Model\Session $customerSession
      * @param \Magento\Index\Model\Indexer $indexer
      * @param Status $stockStatus
-     * @param \Magento\CatalogInventory\Helper\Data $catalogInventoryData
+     * @param \Magento\CatalogInventory\Service\V1\StockItem $stockItemService
      * @param \Magento\CatalogInventory\Helper\Minsaleqty $catalogInventoryMinsaleqty
      * @param \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig
      * @param \Magento\Store\Model\StoreManagerInterface $storeManager
      * @param \Magento\Framework\Locale\FormatInterface $localeFormat
      * @param \Magento\Framework\Math\Division $mathDivision
      * @param \Magento\Framework\Stdlib\DateTime\TimezoneInterface $localeDate
+     * @param \Magento\Catalog\Model\ProductFactory $productFactory
      * @param \Magento\Framework\Model\Resource\AbstractResource $resource
      * @param \Magento\Framework\Data\Collection\Db $resourceCollection
      * @param array $data
@@ -224,13 +256,14 @@ class Item extends \Magento\Framework\Model\AbstractModel
         \Magento\Customer\Model\Session $customerSession,
         \Magento\Index\Model\Indexer $indexer,
         Status $stockStatus,
-        \Magento\CatalogInventory\Helper\Data $catalogInventoryData,
+        \Magento\CatalogInventory\Service\V1\StockItem $stockItemService,
         \Magento\CatalogInventory\Helper\Minsaleqty $catalogInventoryMinsaleqty,
         \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig,
         \Magento\Store\Model\StoreManagerInterface $storeManager,
         \Magento\Framework\Locale\FormatInterface $localeFormat,
         \Magento\Framework\Math\Division $mathDivision,
         \Magento\Framework\Stdlib\DateTime\TimezoneInterface $localeDate,
+        \Magento\Catalog\Model\ProductFactory $productFactory,
         \Magento\Framework\Model\Resource\AbstractResource $resource = null,
         \Magento\Framework\Data\Collection\Db $resourceCollection = null,
         array $data = array()
@@ -240,13 +273,14 @@ class Item extends \Magento\Framework\Model\AbstractModel
         $this->_customerSession = $customerSession;
         $this->_indexer = $indexer;
         $this->_stockStatus = $stockStatus;
-        $this->_catalogInventoryData = $catalogInventoryData;
+        $this->stockItemService = $stockItemService;
         $this->_catalogInventoryMinsaleqty = $catalogInventoryMinsaleqty;
         $this->_scopeConfig = $scopeConfig;
         $this->_storeManager = $storeManager;
         $this->_localeFormat = $localeFormat;
         $this->mathDivision = $mathDivision;
         $this->_localeDate = $localeDate;
+        $this->productFactory = $productFactory;
     }
 
     /**
@@ -376,11 +410,8 @@ class Item extends \Magento\Framework\Model\AbstractModel
 
         $this->setProduct($product);
         $product->setStockItem($this);
-
         $product->setIsInStock($this->getIsInStock());
-
         $this->_stockStatus->assignProduct($product, $this->getStockId(), $this->getStockStatus());
-
         return $this;
     }
 
@@ -391,12 +422,15 @@ class Item extends \Magento\Framework\Model\AbstractModel
      */
     public function getMinQty()
     {
-        return (double)($this->getUseConfigMinQty() ? $this->_scopeConfig->getValue(
-            self::XML_PATH_MIN_QTY,
-            \Magento\Store\Model\ScopeInterface::SCOPE_STORE
-        ) : $this->getData(
-            'min_qty'
-        ));
+        if ($this->getUseConfigMinQty()) {
+            $minQty = (float) $this->_scopeConfig->getValue(
+                self::XML_PATH_MIN_QTY,
+                \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+            );
+        } else {
+            $minQty = (float) $this->getData('min_qty');
+        }
+        return $minQty;
     }
 
     /**
@@ -433,13 +467,12 @@ class Item extends \Magento\Framework\Model\AbstractModel
     {
         $customerGroupId = $this->getCustomerGroupId();
         if (!isset($this->_minSaleQtyCache[$customerGroupId])) {
-            $minSaleQty = $this->getUseConfigMinSaleQty() ? $this->_catalogInventoryMinsaleqty->getConfigValue(
-                $customerGroupId
-            ) : $this->getData(
-                'min_sale_qty'
-            );
-
-            $this->_minSaleQtyCache[$customerGroupId] = empty($minSaleQty) ? 0 : (double)$minSaleQty;
+            if ($this->getUseConfigMinSaleQty()) {
+                $minSaleQty = $this->_catalogInventoryMinsaleqty->getConfigValue($customerGroupId);
+            } else {
+                $minSaleQty = $this->getData('min_sale_qty');
+            }
+            $this->_minSaleQtyCache[$customerGroupId] = empty($minSaleQty) ? 0 : (float) $minSaleQty;
         }
 
         return $this->_minSaleQtyCache[$customerGroupId] ? $this->_minSaleQtyCache[$customerGroupId] : null;
@@ -452,12 +485,15 @@ class Item extends \Magento\Framework\Model\AbstractModel
      */
     public function getMaxSaleQty()
     {
-        return (double)($this->getUseConfigMaxSaleQty() ? $this->_scopeConfig->getValue(
-            self::XML_PATH_MAX_SALE_QTY,
-            \Magento\Store\Model\ScopeInterface::SCOPE_STORE
-        ) : $this->getData(
-            'max_sale_qty'
-        ));
+        if ($this->getUseConfigMaxSaleQty()) {
+            $maxSaleQty = (float) $this->_scopeConfig->getValue(
+                self::XML_PATH_MAX_SALE_QTY,
+                \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+            );
+        } else {
+            $maxSaleQty = (float) $this->getData('max_sale_qty');
+        }
+        return $maxSaleQty;
     }
 
     /**
@@ -468,12 +504,12 @@ class Item extends \Magento\Framework\Model\AbstractModel
     public function getNotifyStockQty()
     {
         if ($this->getUseConfigNotifyStockQty()) {
-            return (double)$this->_scopeConfig->getValue(
+            return (float) $this->_scopeConfig->getValue(
                 self::XML_PATH_NOTIFY_STOCK_QTY,
                 \Magento\Store\Model\ScopeInterface::SCOPE_STORE
             );
         }
-        return (double)$this->getData('notify_stock_qty');
+        return (float) $this->getData('notify_stock_qty');
     }
 
     /**
@@ -489,7 +525,7 @@ class Item extends \Magento\Framework\Model\AbstractModel
                 \Magento\Store\Model\ScopeInterface::SCOPE_STORE
             );
         }
-        return (bool)$this->getData('enable_qty_increments');
+        return (bool) $this->getData('enable_qty_increments');
     }
 
     /**
@@ -501,16 +537,16 @@ class Item extends \Magento\Framework\Model\AbstractModel
     {
         if ($this->_qtyIncrements === null) {
             if ($this->getEnableQtyIncrements()) {
-                $this->_qtyIncrements = (double)($this->getUseConfigQtyIncrements() ? $this->_scopeConfig->getValue(
-                    self::XML_PATH_QTY_INCREMENTS,
-                    \Magento\Store\Model\ScopeInterface::SCOPE_STORE
-                ) : $this->getData(
-                    'qty_increments'
-                ));
-                if ($this->_qtyIncrements <= 0) {
-                    $this->_qtyIncrements = false;
+                if ($this->getUseConfigQtyIncrements()) {
+                    $this->_qtyIncrements = (float) $this->_scopeConfig->getValue(
+                        self::XML_PATH_QTY_INCREMENTS,
+                        \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+                    );
+                } else {
+                    $this->_qtyIncrements = (float) $this->getData('qty_increments');
                 }
-            } else {
+            }
+            if ($this->_qtyIncrements <= 0) {
                 $this->_qtyIncrements = false;
             }
         }
@@ -525,13 +561,20 @@ class Item extends \Magento\Framework\Model\AbstractModel
      */
     public function getDefaultQtyIncrements()
     {
-        return $this->_scopeConfig->isSetFlag(
+        $isEnabledQtyIncrements = $this->_scopeConfig->isSetFlag(
             self::XML_PATH_ENABLE_QTY_INCREMENTS,
             \Magento\Store\Model\ScopeInterface::SCOPE_STORE
-        ) ? (int)$this->_scopeConfig->getValue(
-            self::XML_PATH_QTY_INCREMENTS,
-            \Magento\Store\Model\ScopeInterface::SCOPE_STORE
-        ) : false;
+        );
+
+        $result = false;
+        if ($isEnabledQtyIncrements) {
+            $result = (int) $this->_scopeConfig->getValue(
+                self::XML_PATH_QTY_INCREMENTS,
+                \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+            );
+        }
+
+        return $result;
     }
 
     /**
@@ -542,7 +585,7 @@ class Item extends \Magento\Framework\Model\AbstractModel
     public function getBackorders()
     {
         if ($this->getUseConfigBackorders()) {
-            return (int)$this->_scopeConfig->getValue(
+            return (int) $this->_scopeConfig->getValue(
                 self::XML_PATH_BACKORDERS,
                 \Magento\Store\Model\ScopeInterface::SCOPE_STORE
             );
@@ -558,7 +601,7 @@ class Item extends \Magento\Framework\Model\AbstractModel
     public function getManageStock()
     {
         if ($this->getUseConfigManageStock()) {
-            return (int)$this->_scopeConfig->isSetFlag(
+            return (int) $this->_scopeConfig->isSetFlag(
                 self::XML_PATH_MANAGE_STOCK,
                 \Magento\Store\Model\ScopeInterface::SCOPE_STORE
             );
@@ -599,7 +642,6 @@ class Item extends \Magento\Framework\Model\AbstractModel
                     break;
                 default:
                     return false;
-                    break;
             }
         }
         return true;
@@ -686,32 +728,20 @@ class Item extends \Magento\Framework\Model\AbstractModel
         }
 
         if ($this->getMinSaleQty() && $qty < $this->getMinSaleQty()) {
-            $result->setHasError(
-                true
-            )->setMessage(
-                __('The fewest you may purchase is %1.', $this->getMinSaleQty() * 1)
-            )->setErrorCode(
-                'qty_min'
-            )->setQuoteMessage(
-                __('Please correct the quantity for some products.')
-            )->setQuoteMessageIndex(
-                'qty'
-            );
+            $result->setHasError(true)
+                ->setMessage(__('The fewest you may purchase is %1.', $this->getMinSaleQty() * 1))
+                ->setErrorCode('qty_min')
+                ->setQuoteMessage(__('Please correct the quantity for some products.'))
+                ->setQuoteMessageIndex('qty');
             return $result;
         }
 
         if ($this->getMaxSaleQty() && $qty > $this->getMaxSaleQty()) {
-            $result->setHasError(
-                true
-            )->setMessage(
-                __('The most you may purchase is %1.', $this->getMaxSaleQty() * 1)
-            )->setErrorCode(
-                'qty_max'
-            )->setQuoteMessage(
-                __('Please correct the quantity for some products.')
-            )->setQuoteMessageIndex(
-                'qty'
-            );
+            $result->setHasError(true)
+                ->setMessage(__('The most you may purchase is %1.', $this->getMaxSaleQty() * 1))
+                ->setErrorCode('qty_max')
+                ->setQuoteMessage(__('Please correct the quantity for some products.'))
+                ->setQuoteMessageIndex('qty');
             return $result;
         }
 
@@ -725,15 +755,10 @@ class Item extends \Magento\Framework\Model\AbstractModel
         }
 
         if (!$this->getIsInStock()) {
-            $result->setHasError(
-                true
-            )->setMessage(
-                __('This product is out of stock.')
-            )->setQuoteMessage(
-                __('Some of the products are currently out of stock.')
-            )->setQuoteMessageIndex(
-                'stock'
-            );
+            $result->setHasError(true)
+                ->setMessage(__('This product is out of stock.'))
+                ->setQuoteMessage(__('Some of the products are currently out of stock.'))
+                ->setQuoteMessageIndex('stock');
             $result->setItemUseOldQty(true);
             return $result;
         }
@@ -746,25 +771,25 @@ class Item extends \Magento\Framework\Model\AbstractModel
             if ($this->getQty() - $summaryQty < 0) {
                 if ($this->getProductName()) {
                     if ($this->getIsChildItem()) {
-                        $backorderQty = $this->getQty() > 0 ? ($summaryQty - $this->getQty()) * 1 : $qty * 1;
-                        if ($backorderQty > $qty) {
-                            $backorderQty = $qty;
+                        $backOrderQty = $this->getQty() > 0 ? ($summaryQty - $this->getQty()) * 1 : $qty * 1;
+                        if ($backOrderQty > $qty) {
+                            $backOrderQty = $qty;
                         }
 
-                        $result->setItemBackorders($backorderQty);
+                        $result->setItemBackorders($backOrderQty);
                     } else {
                         $orderedItems = (int)$this->getOrderedItems();
 
                         // Available item qty in stock excluding item qty in other quotes
                         $qtyAvailable = ($this->getQty() - ($summaryQty - $qty))* 1;
                         if ($qtyAvailable > 0) {
-                            $backorderQty = $qty * 1 - $qtyAvailable;
+                            $backOrderQty = $qty * 1 - $qtyAvailable;
                         } else {
-                            $backorderQty = $qty * 1;
+                            $backOrderQty = $qty * 1;
                         }
 
-                        if ($backorderQty > 0) {
-                            $result->setItemBackorders($backorderQty);
+                        if ($backOrderQty > 0) {
+                            $result->setItemBackorders($backOrderQty);
                         }
                         $this->setOrderedItems($orderedItems + $qty);
                     }
@@ -775,7 +800,7 @@ class Item extends \Magento\Framework\Model\AbstractModel
                                 __(
                                     'We don\'t have as many "%1" as you requested, but we\'ll back order the remaining %2.',
                                     $this->getProductName(),
-                                    $backorderQty * 1
+                                    $backOrderQty * 1
                                 )
                             );
                         } else {
@@ -783,7 +808,7 @@ class Item extends \Magento\Framework\Model\AbstractModel
                                 __(
                                     'We don\'t have "%1" in the requested quantity, so we\'ll back order the remaining %2.',
                                     $this->getProductName(),
-                                    $backorderQty * 1
+                                    $backOrderQty * 1
                                 )
                             );
                         }
@@ -795,7 +820,7 @@ class Item extends \Magento\Framework\Model\AbstractModel
                 }
             } else {
                 if (!$this->getIsChildItem()) {
-                    $this->setOrderedItems($qty + (int)$this->getOrderedItems());
+                    $this->setOrderedItems($qty + (int) $this->getOrderedItems());
                 }
             }
         }
@@ -819,15 +844,10 @@ class Item extends \Magento\Framework\Model\AbstractModel
         $qtyIncrements = $this->getQtyIncrements();
 
         if ($qtyIncrements && $this->mathDivision->getExactDivision($qty, $qtyIncrements) != 0) {
-            $result->setHasError(
-                true
-            )->setQuoteMessage(
-                __('Please correct the quantity for some products.')
-            )->setErrorCode(
-                'qty_increments'
-            )->setQuoteMessageIndex(
-                'qty'
-            );
+            $result->setHasError(true)
+                ->setQuoteMessage(__('Please correct the quantity for some products.'))
+                ->setErrorCode('qty_increments')
+                ->setQuoteMessageIndex('qty');
             if ($this->getIsChildItem()) {
                 $result->setMessage(
                     __('You can buy %1 only in increments of %2.', $this->getProductName(), $qtyIncrements * 1)
@@ -888,7 +908,7 @@ class Item extends \Magento\Framework\Model\AbstractModel
             $typeId = $productTypeId;
         }
 
-        $isQty = $this->_catalogInventoryData->isQty($typeId);
+        $isQty = $this->stockItemService->isQty($typeId);
 
         if ($isQty) {
             if ($this->getManageStock() && !$this->verifyStock()) {
@@ -899,20 +919,14 @@ class Item extends \Magento\Framework\Model\AbstractModel
             $this->setLowStockDate(null);
             if ($this->verifyNotification()) {
                 $this->setLowStockDate(
-                    $this->_localeDate->date(
-                        null,
-                        null,
-                        null,
-                        false
-                    )->toString(
-                        \Magento\Framework\Stdlib\DateTime::DATETIME_INTERNAL_FORMAT
-                    )
+                    $this->_localeDate->date(null, null, null, false)
+                        ->toString(\Magento\Framework\Stdlib\DateTime::DATETIME_INTERNAL_FORMAT)
                 );
             }
 
             $this->setStockStatusChangedAuto(0);
             if ($this->hasStockStatusChangedAutomaticallyFlag()) {
-                $this->setStockStatusChangedAuto((int)$this->getStockStatusChangedAutomaticallyFlag());
+                $this->setStockStatusChangedAuto((int) $this->getStockStatusChangedAutomaticallyFlag());
             }
         } else {
             $this->setQty(0);
@@ -922,7 +936,7 @@ class Item extends \Magento\Framework\Model\AbstractModel
     }
 
     /**
-     * Chceck if item should be in stock or out of stock based on $qty param of existing item qty
+     * Check if item should be in stock or out of stock based on $qty param of existing item qty
      *
      * @param float|null $qty
      * @return bool true - item in stock | false - item out of stock
@@ -932,9 +946,9 @@ class Item extends \Magento\Framework\Model\AbstractModel
         if ($qty === null) {
             $qty = $this->getQty();
         }
-        if ($qty !== null &&
-            $this->getBackorders() == \Magento\CatalogInventory\Model\Stock::BACKORDERS_NO &&
-            $qty <= $this->getMinQty()
+        if ($qty !== null
+            && $this->getBackorders() == \Magento\CatalogInventory\Model\Stock::BACKORDERS_NO
+            && $qty <= $this->getMinQty()
         ) {
             return false;
         }
@@ -952,7 +966,7 @@ class Item extends \Magento\Framework\Model\AbstractModel
         if ($qty === null) {
             $qty = $this->getQty();
         }
-        return (double)$qty < $this->getNotifyStockQty();
+        return (float) $qty < $this->getNotifyStockQty();
     }
 
     /**
@@ -993,37 +1007,16 @@ class Item extends \Magento\Framework\Model\AbstractModel
      */
     public function setProduct($product)
     {
-        $this->setProductId(
-            $product->getId()
-        )->setProductName(
-            $product->getName()
-        )->setStoreId(
-            $product->getStoreId()
-        )->setProductName(
-            $product->getName()
-        )->setProductTypeId(
-            $product->getTypeId()
-        )->setProductStatusChanged(
-            $product->dataHasChangedFor('status')
-        )->setProductChangedWebsites(
-            $product->getIsChangedWebsites()
-        );
-
-        $this->_productInstance = $product;
+        $this->setProductId($product->getId())
+            ->setProductName($product->getName())
+            ->setStoreId($product->getStoreId())
+            ->setProductTypeId($product->getTypeId())
+            ->setProductStatusChanged($product->dataHasChangedFor('status'))
+            ->setProductChangedWebsites($product->getIsChangedWebsites());
 
         return $this;
     }
 
-    /**
-     * Returns product instance
-     *
-     * @return Product|null
-     */
-    public function getProduct()
-    {
-        return $this->_productInstance ? $this->_productInstance : $this->_getData('product');
-    }
-
     /**
      * Retrieve stock qty whether product is composite or no
      *
@@ -1033,9 +1026,12 @@ class Item extends \Magento\Framework\Model\AbstractModel
     {
         if (!$this->hasStockQty()) {
             $this->setStockQty(0);
+
+            /** @var Product $product */
+            $product = $this->productFactory->create();
+            $product->load($this->getProductId());
             // prevent possible recursive loop
-            $product = $this->_productInstance;
-            if (!$product || !$product->isComposite()) {
+            if (!$product->isComposite()) {
                 $stockQty = $this->getQty();
             } else {
                 $stockQty = null;
@@ -1047,34 +1043,18 @@ class Item extends \Magento\Framework\Model\AbstractModel
                             $qty += $childProduct->getStockItem()->getStockQty();
                         }
                     }
-                    if (is_null($stockQty) || $qty < $stockQty) {
+                    if (null === $stockQty || $qty < $stockQty) {
                         $stockQty = $qty;
                     }
                 }
             }
-            $stockQty = (double)$stockQty;
-            if ($stockQty < 0 ||
-                !$this->getManageStock() ||
-                !$this->getIsInStock() ||
-                $product && !$product->isSaleable()
-            ) {
+            $stockQty = (float) $stockQty;
+            if ($stockQty < 0 || !$this->getManageStock() || !$this->getIsInStock() || !$product->isSaleable()) {
                 $stockQty = 0;
             }
             $this->setStockQty($stockQty);
         }
-        return $this->getData('stock_qty');
-    }
-
-    /**
-     * Reset model data
-     * @return $this
-     */
-    public function reset()
-    {
-        if ($this->_productInstance) {
-            $this->_productInstance = null;
-        }
-        return $this;
+        return (float) $this->getData('stock_qty');
     }
 
     /**
@@ -1096,7 +1076,7 @@ class Item extends \Magento\Framework\Model\AbstractModel
      */
     protected function _isQtyCheckApplicable()
     {
-        return (bool)$this->getManageStock();
+        return (bool) $this->getManageStock();
     }
 
     /**
diff --git a/app/code/Magento/CatalogInventory/Model/Stock/ItemRegistry.php b/app/code/Magento/CatalogInventory/Model/Stock/ItemRegistry.php
new file mode 100644
index 00000000000..7f3d7deef5a
--- /dev/null
+++ b/app/code/Magento/CatalogInventory/Model/Stock/ItemRegistry.php
@@ -0,0 +1,74 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogInventory\Model\Stock;
+
+/**
+ * Stock item registry
+ */
+class ItemRegistry extends \Magento\Framework\Model\AbstractModel
+{
+    /**
+     * @var \Magento\CatalogInventory\Model\Stock\Item[]
+     */
+    protected $stockItemRegistry;
+
+    /**
+     * @var \Magento\CatalogInventory\Model\Stock\ItemFactory
+     */
+    protected $stockItemFactory;
+
+    /**
+     * @var \Magento\CatalogInventory\Model\Resource\Stock\Item
+     */
+    protected $stockItemResource;
+
+    /**
+     * @param ItemFactory $stockItemFactory
+     * @param \Magento\CatalogInventory\Model\Resource\Stock\Item $stockItemResource
+     */
+    public function __construct(
+        ItemFactory $stockItemFactory,
+        \Magento\CatalogInventory\Model\Resource\Stock\Item $stockItemResource
+    ) {
+        $this->stockItemFactory = $stockItemFactory;
+        $this->stockItemResource = $stockItemResource;
+    }
+
+    /**
+     * @param int $productId
+     * @return \Magento\CatalogInventory\Model\Stock\Item
+     */
+    public function retrieve($productId)
+    {
+        if (!isset($this->stockItemRegistry[$productId])) {
+            /** @var \Magento\CatalogInventory\Model\Stock\Item $stockItem */
+            $stockItem = $this->stockItemFactory->create();
+
+            $this->stockItemResource->loadByProductId($stockItem, $productId);
+            $this->stockItemRegistry[$productId] = $stockItem;
+        }
+
+        return $this->stockItemRegistry[$productId];
+    }
+}
diff --git a/app/code/Magento/CatalogInventory/Model/Stock/Status.php b/app/code/Magento/CatalogInventory/Model/Stock/Status.php
index 677b6212ac6..747c344d39a 100644
--- a/app/code/Magento/CatalogInventory/Model/Stock/Status.php
+++ b/app/code/Magento/CatalogInventory/Model/Stock/Status.php
@@ -23,6 +23,7 @@
  */
 namespace Magento\CatalogInventory\Model\Stock;
 
+use Magento\CatalogInventory\Model\Stock;
 use Magento\Catalog\Model\Product\Type\AbstractType;
 use Magento\Catalog\Model\Product\Type;
 use Magento\Catalog\Model\Product\Attribute\Source\Status as ProductStatus;
@@ -31,15 +32,15 @@ use Magento\Catalog\Model\Product\Attribute\Source\Status as ProductStatus;
  * CatalogInventory Stock Status per website Model
  *
  * @method int getProductId()
- * @method \Magento\CatalogInventory\Model\Stock\Status setProductId(int $value)
+ * @method Status setProductId(int $value)
  * @method int getWebsiteId()
- * @method \Magento\CatalogInventory\Model\Stock\Status setWebsiteId(int $value)
+ * @method Status setWebsiteId(int $value)
  * @method int getStockId()
- * @method \Magento\CatalogInventory\Model\Stock\Status setStockId(int $value)
+ * @method Status setStockId(int $value)
  * @method float getQty()
- * @method \Magento\CatalogInventory\Model\Stock\Status setQty(float $value)
+ * @method Status setQty(float $value)
  * @method int getStockStatus()
- * @method \Magento\CatalogInventory\Model\Stock\Status setStockStatus(int $value)
+ * @method Status setStockStatus(int $value)
  */
 class Status extends \Magento\Framework\Model\AbstractModel
 {
@@ -49,7 +50,6 @@ class Status extends \Magento\Framework\Model\AbstractModel
     const STATUS_OUT_OF_STOCK = 0;
 
     const STATUS_IN_STOCK = 1;
-
     /**#@-*/
 
     /**
@@ -158,7 +158,7 @@ class Status extends \Magento\Framework\Model\AbstractModel
      * Retrieve Product Type Instance By Product Type
      *
      * @param string $productType
-     * @return AbstractType|false
+     * @return AbstractType|bool
      */
     public function getProductTypeInstance($productType)
     {
@@ -178,7 +178,9 @@ class Status extends \Magento\Framework\Model\AbstractModel
     public function getWebsites($websiteId = null)
     {
         if (is_null($this->_websites)) {
-            $this->_websites = $this->getResource()->getWebsiteStores();
+            /** @var \Magento\CatalogInventory\Model\Resource\Stock\Status $resource */
+            $resource = $this->getResource();
+            $this->_websites = $resource->getWebsiteStores();
         }
 
         $websites = $this->_websites;
@@ -189,43 +191,6 @@ class Status extends \Magento\Framework\Model\AbstractModel
         return $websites;
     }
 
-    /**
-     * Retrieve Default website store Id
-     *
-     * @param int $websiteId
-     * @return int
-     */
-    public function getWebsiteDefaultStoreId($websiteId)
-    {
-        $websites = $this->getWebsites();
-        if (isset($websites[$websiteId])) {
-            return $websites[$websiteId];
-        }
-        return 0;
-    }
-
-    /**
-     * Change Stock Item status process
-     *
-     * @param Item $item
-     * @return $this
-     */
-    public function changeItemStatus(Item $item)
-    {
-        $productId = $item->getProductId();
-        if (!($productType = $item->getProductTypeId())) {
-            $productType = $this->getProductType($productId);
-        }
-
-        $status = (int)$item->getIsInStock();
-        $qty = (int)$item->getQty();
-
-        $this->_processChildren($productId, $productType, $qty, $status, $item->getStockId());
-        $this->_processParents($productId, $item->getStockId());
-
-        return $this;
-    }
-
     /**
      * Assign Stock Status to Product
      *
@@ -234,8 +199,11 @@ class Status extends \Magento\Framework\Model\AbstractModel
      * @param int $stockStatus
      * @return $this
      */
-    public function assignProduct(\Magento\Catalog\Model\Product $product, $stockId = 1, $stockStatus = null)
-    {
+    public function assignProduct(
+        \Magento\Catalog\Model\Product $product,
+        $stockId = Stock::DEFAULT_STOCK_ID,
+        $stockStatus = null
+    ) {
         if (is_null($stockStatus)) {
             $websiteId = $product->getStore()->getWebsiteId();
             $status = $this->getProductStockStatus($product->getId(), $websiteId, $stockId);
@@ -257,7 +225,9 @@ class Status extends \Magento\Framework\Model\AbstractModel
     {
         $lastProductId = 0;
         while (true) {
-            $productCollection = $this->getResource()->getProductCollection($lastProductId);
+            /** @var \Magento\CatalogInventory\Model\Resource\Stock\Status $resource */
+            $resource = $this->getResource();
+            $productCollection = $resource->getProductCollection($lastProductId);
             if (!$productCollection) {
                 break;
             }
@@ -317,7 +287,7 @@ class Status extends \Magento\Framework\Model\AbstractModel
         $productType,
         $qty = 0,
         $status = self::STATUS_IN_STOCK,
-        $stockId = 1,
+        $stockId = Stock::DEFAULT_STOCK_ID,
         $websiteId = null
     ) {
         if ($status == self::STATUS_OUT_OF_STOCK) {
@@ -333,7 +303,8 @@ class Status extends \Magento\Framework\Model\AbstractModel
             $statuses[$websiteId] = $status;
         }
 
-        if (!($typeInstance = $this->getProductTypeInstance($productType))) {
+        $typeInstance = $this->getProductTypeInstance($productType);
+        if (!$typeInstance) {
             return $this;
         }
 
@@ -347,28 +318,23 @@ class Status extends \Magento\Framework\Model\AbstractModel
             foreach ($websites as $websiteId => $storeId) {
                 $childrenStatus = $this->getProductStatus($childrenIds, $storeId);
                 $childrenStock = $this->getProductStockStatus($childrenIds, $websiteId, $stockId);
-
                 $websiteStatus = $statuses[$websiteId];
                 foreach ($requiredChildrenIds as $groupedChildrenIds) {
                     $optionStatus = false;
                     foreach ($groupedChildrenIds as $childId) {
-                        if (isset(
-                            $childrenStatus[$childId]
-                        ) && isset(
-                            $childrenWebsites[$childId]
-                        ) && in_array(
-                            $websiteId,
-                            $childrenWebsites[$childId]
-                        ) && $childrenStatus[$childId] == ProductStatus::STATUS_ENABLED && isset(
-                            $childrenStock[$childId]
-                        ) && $childrenStock[$childId] == self::STATUS_IN_STOCK
+                        if (isset($childrenStatus[$childId])
+                            && isset($childrenWebsites[$childId])
+                            && in_array($websiteId, $childrenWebsites[$childId])
+                            && $childrenStatus[$childId] == ProductStatus::STATUS_ENABLED
+                            && isset($childrenStock[$childId])
+                            && $childrenStock[$childId] == self::STATUS_IN_STOCK
                         ) {
                             $optionStatus = true;
                         }
                     }
                     $websiteStatus = $websiteStatus && $optionStatus;
                 }
-                $statuses[$websiteId] = (int)$websiteStatus;
+                $statuses[$websiteId] = (int) $websiteStatus;
             }
         }
 
@@ -387,7 +353,7 @@ class Status extends \Magento\Framework\Model\AbstractModel
      * @param int $websiteId
      * @return $this
      */
-    protected function _processParents($productId, $stockId = 1, $websiteId = null)
+    protected function _processParents($productId, $stockId = Stock::DEFAULT_STOCK_ID, $websiteId = null)
     {
         $parentIds = array();
         foreach ($this->getProductTypeInstances() as $typeInstance) {
@@ -430,9 +396,16 @@ class Status extends \Magento\Framework\Model\AbstractModel
      * @param int|null $websiteId
      * @return $this
      */
-    public function saveProductStatus($productId, $status, $qty = 0, $stockId = 1, $websiteId = null)
-    {
-        $this->getResource()->saveProductStatus($this, $productId, $status, $qty, $stockId, $websiteId);
+    public function saveProductStatus(
+        $productId,
+        $status,
+        $qty = 0,
+        $stockId = Stock::DEFAULT_STOCK_ID,
+        $websiteId = null
+    ) {
+        /** @var \Magento\CatalogInventory\Model\Resource\Stock\Status $resource */
+        $resource = $this->getResource();
+        $resource->saveProductStatus($this, $productId, $status, $qty, $stockId, $websiteId);
         return $this;
     }
 
@@ -444,9 +417,11 @@ class Status extends \Magento\Framework\Model\AbstractModel
      * @param int $stockId
      * @return array
      */
-    public function getProductStockStatus($productIds, $websiteId, $stockId = 1)
+    public function getProductStockStatus($productIds, $websiteId, $stockId = Stock::DEFAULT_STOCK_ID)
     {
-        return $this->getResource()->getProductStockStatus($productIds, $websiteId, $stockId);
+        /** @var \Magento\CatalogInventory\Model\Resource\Stock\Status $resource */
+        $resource = $this->getResource();
+        return $resource->getProductStockStatus($productIds, $websiteId, $stockId);
     }
 
     /**
@@ -458,20 +433,9 @@ class Status extends \Magento\Framework\Model\AbstractModel
      */
     public function getProductStatus($productIds, $storeId = null)
     {
-        return $this->getResource()->getProductStatus($productIds, $storeId);
-    }
-
-    /**
-     * Retrieve Product(s) Data array
-     *
-     * @param int|int[] $productIds
-     * @param int $websiteId
-     * @param int $stockId
-     * @return array
-     */
-    public function getProductData($productIds, $websiteId, $stockId = 1)
-    {
-        return $this->getResource()->getProductData($productIds, $websiteId, $stockId);
+        /** @var \Magento\CatalogInventory\Model\Resource\Stock\Status $resource */
+        $resource = $this->getResource();
+        return $resource->getProductStatus($productIds, $storeId);
     }
 
     /**
@@ -482,7 +446,9 @@ class Status extends \Magento\Framework\Model\AbstractModel
      */
     public function getProductType($productId)
     {
-        $types = $this->getResource()->getProductsType($productId);
+        /** @var \Magento\CatalogInventory\Model\Resource\Stock\Status $resource */
+        $resource = $this->getResource();
+        $types = $resource->getProductsType($productId);
         if (isset($types[$productId])) {
             return $types[$productId];
         }
@@ -498,7 +464,9 @@ class Status extends \Magento\Framework\Model\AbstractModel
      */
     public function getProductsType($productIds)
     {
-        return $this->getResource()->getProductsType($productIds);
+        /** @var \Magento\CatalogInventory\Model\Resource\Stock\Status $resource */
+        $resource = $this->getResource();
+        return $resource->getProductsType($productIds);
     }
 
     /**
@@ -512,11 +480,11 @@ class Status extends \Magento\Framework\Model\AbstractModel
     public function addStockStatusToProducts($productCollection, $websiteId = null, $stockId = null)
     {
         if ($stockId === null) {
-            $stockId = \Magento\CatalogInventory\Model\Stock::DEFAULT_STOCK_ID;
+            $stockId = Stock::DEFAULT_STOCK_ID;
         }
         if ($websiteId === null) {
             $websiteId = $this->_storeManager->getStore()->getWebsiteId();
-            if ((int)$websiteId == 0 && $productCollection->getStoreId()) {
+            if ((int) $websiteId == 0 && $productCollection->getStoreId()) {
                 $websiteId = $this->_storeManager->getStore($productCollection->getStoreId())->getWebsiteId();
             }
         }
@@ -552,7 +520,8 @@ class Status extends \Magento\Framework\Model\AbstractModel
      */
     public function addStockStatusToSelect(\Magento\Framework\DB\Select $select, \Magento\Store\Model\Website $website)
     {
-        $this->_getResource()->addStockStatusToSelect($select, $website);
+        $resource = $this->_getResource();
+        $resource->addStockStatusToSelect($select, $website);
         return $this;
     }
 
@@ -570,7 +539,8 @@ class Status extends \Magento\Framework\Model\AbstractModel
             return $this;
         }
 
-        $this->_getResource()->prepareCatalogProductIndexSelect($select, $entityField, $websiteField);
+        $resource = $this->_getResource();
+        $resource->prepareCatalogProductIndexSelect($select, $entityField, $websiteField);
 
         return $this;
     }
@@ -583,7 +553,8 @@ class Status extends \Magento\Framework\Model\AbstractModel
      */
     public function addIsInStockFilterToCollection($collection)
     {
-        $this->_getResource()->addIsInStockFilterToCollection($collection);
+        $resource = $this->_getResource();
+        $resource->addIsInStockFilterToCollection($collection);
         return $this;
     }
 
@@ -595,8 +566,8 @@ class Status extends \Magento\Framework\Model\AbstractModel
     public static function getAllOptions()
     {
         return array(
-            array('value' => \Magento\CatalogInventory\Model\Stock::STOCK_IN_STOCK, 'label' => __('In Stock')),
-            array('value' => \Magento\CatalogInventory\Model\Stock::STOCK_OUT_OF_STOCK, 'label' => __('Out of Stock'))
+            array('value' => Stock::STOCK_IN_STOCK, 'label' => __('In Stock')),
+            array('value' => Stock::STOCK_OUT_OF_STOCK, 'label' => __('Out of Stock'))
         );
     }
 }
diff --git a/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Minqty.php b/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Minqty.php
index a94f557d15e..5ebeb2b2218 100644
--- a/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Minqty.php
+++ b/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Minqty.php
@@ -22,13 +22,11 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
+namespace Magento\CatalogInventory\Model\System\Config\Backend;
+
 /**
  * Minimum product qty backend model
- *
- * @author     Magento Core Team <core@magentocommerce.com>
  */
-namespace Magento\CatalogInventory\Model\System\Config\Backend;
-
 class Minqty extends \Magento\Framework\App\Config\Value
 {
     /**
@@ -39,8 +37,8 @@ class Minqty extends \Magento\Framework\App\Config\Value
     protected function _beforeSave()
     {
         parent::_beforeSave();
-        $minQty = (int)$this->getValue() >= 0 ? (int)$this->getValue() : (int)$this->getOldValue();
-        $this->setValue((string)$minQty);
+        $minQty = (int) $this->getValue() >= 0 ? (int) $this->getValue() : (int) $this->getOldValue();
+        $this->setValue((string) $minQty);
         return $this;
     }
 }
diff --git a/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Minsaleqty.php b/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Minsaleqty.php
index 31d6c3274f8..92224821660 100644
--- a/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Minsaleqty.php
+++ b/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Minsaleqty.php
@@ -21,13 +21,11 @@
  * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
+namespace Magento\CatalogInventory\Model\System\Config\Backend;
 
 /**
  * Backend for serialized array data
- *
  */
-namespace Magento\CatalogInventory\Model\System\Config\Backend;
-
 class Minsaleqty extends \Magento\Framework\App\Config\Value
 {
     /**
diff --git a/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Qtyincrements.php b/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Qtyincrements.php
index 756ff5a7ca5..37054778ea0 100644
--- a/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Qtyincrements.php
+++ b/app/code/Magento/CatalogInventory/Model/System/Config/Backend/Qtyincrements.php
@@ -21,15 +21,13 @@
  * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
-
-/**
- * Backend for qty increments
- *
- */
 namespace Magento\CatalogInventory\Model\System\Config\Backend;
 
 use Magento\Framework\Model\Exception;
 
+/**
+ * Backend for qty increments
+ */
 class Qtyincrements extends \Magento\Framework\App\Config\Value
 {
     /**
diff --git a/app/code/Magento/CatalogInventory/Service/V1/Data/StockItem.php b/app/code/Magento/CatalogInventory/Service/V1/Data/StockItem.php
new file mode 100644
index 00000000000..daaa7399804
--- /dev/null
+++ b/app/code/Magento/CatalogInventory/Service/V1/Data/StockItem.php
@@ -0,0 +1,286 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogInventory\Service\V1\Data;
+
+use Magento\Framework\Service\Data\AbstractObject;
+
+/**
+ * Stock item data object
+ */
+class StockItem extends AbstractObject
+{
+    /**#@+
+     * Stock item object data keys
+     */
+    const ITEM_ID = 'item_id';
+
+    const PRODUCT_ID = 'product_id';
+
+    const STOCK_ID = 'stock_id';
+
+    const QTY = 'qty';
+
+    const MIN_QTY = 'min_qty';
+
+    const USE_CONFIG_MIN_QTY = 'use_config_min_qty';
+
+    const IS_QTY_DECIMAL = 'is_qty_decimal';
+
+    const BACKORDERS = 'backorders';
+
+    const USE_CONFIG_BACKORDERS = 'use_config_backorders';
+
+    const MIN_SALE_QTY = 'min_sale_qty';
+
+    const USE_CONFIG_MIN_SALE_QTY = 'use_config_min_sale_qty';
+
+    const MAX_SALE_QTY = 'max_sale_qty';
+
+    const USE_CONFIG_MAX_SALE_QTY = 'use_config_max_sale_qty';
+
+    const IS_IN_STOCK = 'is_in_stock';
+
+    const LOW_STOCK_DATE = 'low_stock_date';
+
+    const NOTIFY_STOCK_QTY = 'notify_stock_qty';
+
+    const USE_CONFIG_NOTIFY_STOCK_QTY = 'use_config_notify_stock_qty';
+
+    const MANAGE_STOCK = 'manage_stock';
+
+    const USE_CONFIG_MANAGE_STOCK = 'use_config_manage_stock';
+
+    const STOCK_STATUS_CHANGED_AUTO = 'stock_status_changed_auto';
+
+    const USE_CONFIG_QTY_INCREMENTS = 'use_config_qty_increments';
+
+    const QTY_INCREMENTS = 'qty_increments';
+
+    const USE_CONFIG_ENABLE_QTY_INC = 'use_config_enable_qty_inc';
+
+    const ENABLE_QTY_INCREMENTS = 'enable_qty_increments';
+
+    const IS_DECIMAL_DIVIDED = 'is_decimal_divided';
+    /**#@-*/
+
+    /**
+     * @return int
+     */
+    public function getItemId()
+    {
+        return $this->_get(self::ITEM_ID);
+    }
+
+    /**
+     * @return int
+     */
+    public function getProductId()
+    {
+        return $this->_get(self::PRODUCT_ID);
+    }
+
+    /**
+     * @return int
+     */
+    public function getStockId()
+    {
+        return $this->_get(self::STOCK_ID);
+    }
+
+    /**
+     * @return float
+     */
+    public function getQty()
+    {
+        return $this->_get(self::QTY);
+    }
+
+    /**
+     * @return float
+     */
+    public function getMinQty()
+    {
+        return $this->_get(self::MIN_QTY);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isUseConfigMinQty()
+    {
+        return $this->_get(self::USE_CONFIG_MIN_QTY);
+    }
+
+    /**
+     * @return bool
+     */
+    public function getIsQtyDecimal()
+    {
+        return $this->_get(self::IS_QTY_DECIMAL);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isBackorders()
+    {
+        return $this->_get(self::BACKORDERS);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isUseConfigBackorders()
+    {
+        return $this->_get(self::USE_CONFIG_BACKORDERS);
+    }
+
+    /**
+     * @return float
+     */
+    public function getMinSaleQty()
+    {
+        return $this->_get(self::MIN_SALE_QTY);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isUseConfigMinSaleQty()
+    {
+        return $this->_get(self::USE_CONFIG_MIN_SALE_QTY);
+    }
+
+    /**
+     * @return float
+     */
+    public function getMaxSaleQty()
+    {
+        return $this->_get(self::MAX_SALE_QTY);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isUseConfigMaxSaleQty()
+    {
+        return $this->_get(self::USE_CONFIG_MAX_SALE_QTY);
+    }
+
+    /**
+     * @return bool
+     */
+    public function getIsInStock()
+    {
+        return $this->_get(self::IS_IN_STOCK);
+    }
+
+    /**
+     * @return string
+     */
+    public function getLowStockDate()
+    {
+        return $this->_get(self::LOW_STOCK_DATE);
+    }
+
+    /**
+     * @return float
+     */
+    public function getNotifyStockQty()
+    {
+        return $this->_get(self::NOTIFY_STOCK_QTY);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isUseConfigNotifyStockQty()
+    {
+        return $this->_get(self::USE_CONFIG_NOTIFY_STOCK_QTY);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isManageStock()
+    {
+        return $this->_get(self::MANAGE_STOCK);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isUseConfigManageStock()
+    {
+        return $this->_get(self::USE_CONFIG_MANAGE_STOCK);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isStockStatusChangedAuto()
+    {
+        return $this->_get(self::STOCK_STATUS_CHANGED_AUTO);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isUseConfigQtyIncrements()
+    {
+        return $this->_get(self::USE_CONFIG_QTY_INCREMENTS);
+    }
+
+    /**
+     * @return float
+     */
+    public function getQtyIncrements()
+    {
+        return $this->_get(self::QTY_INCREMENTS);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isUseConfigEnableQtyInc()
+    {
+        return $this->_get(self::USE_CONFIG_ENABLE_QTY_INC);
+    }
+
+    /**
+     * @return bool
+     */
+    public function isEnableQtyIncrements()
+    {
+        return $this->_get(self::ENABLE_QTY_INCREMENTS);
+    }
+
+    /**
+     * @return bool
+     */
+    public function getIsDecimalDivided()
+    {
+        return $this->_get(self::IS_DECIMAL_DIVIDED);
+    }
+}
diff --git a/app/code/Magento/CatalogInventory/Service/V1/Data/StockItemBuilder.php b/app/code/Magento/CatalogInventory/Service/V1/Data/StockItemBuilder.php
new file mode 100644
index 00000000000..35431da1a07
--- /dev/null
+++ b/app/code/Magento/CatalogInventory/Service/V1/Data/StockItemBuilder.php
@@ -0,0 +1,33 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogInventory\Service\V1\Data;
+
+use Magento\Framework\Service\Data\AbstractObjectBuilder;
+
+/**
+ * Stock item data builder
+ */
+class StockItemBuilder extends AbstractObjectBuilder
+{
+}
diff --git a/app/code/Magento/CatalogInventory/Service/V1/StockItem.php b/app/code/Magento/CatalogInventory/Service/V1/StockItem.php
new file mode 100644
index 00000000000..c1d1b9cc4c6
--- /dev/null
+++ b/app/code/Magento/CatalogInventory/Service/V1/StockItem.php
@@ -0,0 +1,340 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogInventory\Service\V1;
+
+/**
+ * Stock item service
+ */
+class StockItem implements StockItemInterface
+{
+    /**
+     * @var \Magento\CatalogInventory\Model\Stock\ItemRegistry
+     */
+    protected $stockItemRegistry;
+
+    /**
+     * @var \Magento\Catalog\Model\ProductTypes\ConfigInterface
+     */
+    protected $config;
+
+    /**
+     * All product types registry in scope of quantity availability
+     *
+     * @var array
+     */
+    protected $isQtyTypeIds;
+
+    /**
+     * @var Data\StockItemBuilder
+     */
+    protected $stockItemBuilder;
+
+    /**
+     * @param \Magento\CatalogInventory\Model\Stock\ItemRegistry $stockItemRegistry
+     * @param \Magento\Catalog\Model\ProductTypes\ConfigInterface $config
+     * @param Data\StockItemBuilder $stockItemBuilder
+     */
+    public function __construct(
+        \Magento\CatalogInventory\Model\Stock\ItemRegistry $stockItemRegistry,
+        \Magento\Catalog\Model\ProductTypes\ConfigInterface $config,
+        Data\StockItemBuilder $stockItemBuilder
+    ) {
+        $this->stockItemRegistry = $stockItemRegistry;
+        $this->config = $config;
+        $this->stockItemBuilder = $stockItemBuilder;
+    }
+
+    /**
+     * @param int $productId
+     * @return \Magento\CatalogInventory\Service\V1\Data\StockItem
+     */
+    public function getStockItem($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        $this->stockItemBuilder->populateWithArray($stockItem->getData());
+        return $this->stockItemBuilder->create();
+    }
+
+    /**
+     * @param \Magento\CatalogInventory\Service\V1\Data\StockItem $stockItemDo
+     * @return $this
+     */
+    public function saveStockItem($stockItemDo)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($stockItemDo->getProductId());
+        $stockItem->setData($stockItemDo->__toArray());
+        $stockItem->save();
+        return $this;
+    }
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @return $this
+     */
+    public function subtractQty($productId, $qty)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        $stockItem->subtractQty($qty);
+        return $this;
+    }
+
+    /**
+     * @param int $productId
+     * @return bool
+     */
+    public function canSubtractQty($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->canSubtractQty();
+    }
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @return $this
+     */
+    public function addQty($productId, $qty)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        $stockItem->addQty($qty);
+        return $this;
+    }
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getMinQty($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getMinQty();
+    }
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getMinSaleQty($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getMinSaleQty();
+    }
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getMaxSaleQty($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getMaxSaleQty();
+    }
+
+    /**
+     * @param int $productId
+     * @return float
+     */
+    public function getNotifyStockQty($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getNotifyStockQty();
+    }
+
+    /**
+     * @param int $productId
+     * @return bool
+     */
+    public function getEnableQtyIncrements($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getEnableQtyIncrements();
+    }
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getQtyIncrements($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getQtyIncrements();
+    }
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getBackorders($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getBackorders();
+    }
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getManageStock($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getManageStock();
+    }
+
+    /**
+     * @param int $productId
+     * @return bool
+     */
+    public function getCanBackInStock($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getCanBackInStock();
+    }
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @return bool
+     */
+    public function checkQty($productId, $qty)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->checkQty($qty);
+    }
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @return bool
+     */
+    public function suggestQty($productId, $qty)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->suggestQty($qty);
+    }
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @param int $summaryQty
+     * @param int $origQty
+     * @return \Magento\Framework\Object
+     */
+    public function checkQuoteItemQty($productId, $qty, $summaryQty, $origQty = 0)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->checkQuoteItemQty($qty, $summaryQty, $origQty);
+    }
+
+    /**
+     * @param int $productId
+     * @param int|null $qty
+     * @return bool
+     */
+    public function verifyStock($productId, $qty = null)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->verifyStock($qty);
+    }
+
+    /**
+     * @param int $productId
+     * @param int|null $qty
+     * @return bool
+     */
+    public function verifyNotification($productId, $qty = null)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->verifyNotification($qty);
+    }
+
+    /**
+     * @param int $productId
+     * @return bool
+     */
+    public function getIsInStock($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getIsInStock();
+    }
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getStockQty($productId)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->getStockQty();
+    }
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @return \Magento\Framework\Object
+     */
+    public function checkQtyIncrements($productId, $qty)
+    {
+        $stockItem = $this->stockItemRegistry->retrieve($productId);
+        return $stockItem->checkQtyIncrements($qty);
+    }
+
+    /**
+     * @param int $productTypeId
+     * @return bool
+     */
+    public function isQty($productTypeId)
+    {
+        $this->getIsQtyTypeIds();
+        if (!isset($this->isQtyTypeIds[$productTypeId])) {
+            return false;
+        }
+        return $this->isQtyTypeIds[$productTypeId];
+    }
+
+    /**
+     * @param int|null $filter
+     * @return bool
+     */
+    public function getIsQtyTypeIds($filter = null)
+    {
+        if (null === $this->isQtyTypeIds) {
+            $this->isQtyTypeIds = array();
+
+            foreach ($this->config->getAll() as $typeId => $typeConfig) {
+                $this->isQtyTypeIds[$typeId] = isset($typeConfig['is_qty']) ? $typeConfig['is_qty'] : false;
+            }
+        }
+        if (null === $filter) {
+            return $this->isQtyTypeIds;
+        }
+        $result = $this->isQtyTypeIds;
+        foreach ($result as $key => $value) {
+            if ($value !== $filter) {
+                unset($result[$key]);
+            }
+        }
+        return $result;
+    }
+}
diff --git a/app/code/Magento/CatalogInventory/Service/V1/StockItemInterface.php b/app/code/Magento/CatalogInventory/Service/V1/StockItemInterface.php
new file mode 100644
index 00000000000..fa2d737de7a
--- /dev/null
+++ b/app/code/Magento/CatalogInventory/Service/V1/StockItemInterface.php
@@ -0,0 +1,184 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogInventory\Service\V1;
+
+/**
+ * Stock item interface
+ */
+interface StockItemInterface
+{
+    /**
+     * @param int $productId
+     * @return \Magento\CatalogInventory\Service\V1\Data\StockItem
+     */
+    public function getStockItem($productId);
+
+    /**
+     * @param \Magento\CatalogInventory\Service\V1\Data\StockItem $stockItem
+     * @return \Magento\CatalogInventory\Service\V1\Data\StockItem
+     */
+    public function saveStockItem($stockItem);
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @return $this
+     */
+    public function subtractQty($productId, $qty);
+
+    /**
+     * @param int $productId
+     * @return bool
+     */
+    public function canSubtractQty($productId);
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @return $this
+     */
+    public function addQty($productId, $qty);
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getMinQty($productId);
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getMinSaleQty($productId);
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getMaxSaleQty($productId);
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getNotifyStockQty($productId);
+
+    /**
+     * @param int $productId
+     * @return bool
+     */
+    public function getEnableQtyIncrements($productId);
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getQtyIncrements($productId);
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getBackorders($productId);
+
+    /**
+     * @param int $productId
+     * @return int mixed
+     */
+    public function getManageStock($productId);
+
+    /**
+     * @param int $productId
+     * @return bool
+     */
+    public function getCanBackInStock($productId);
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @return bool
+     */
+    public function checkQty($productId, $qty);
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @return bool
+     */
+    public function suggestQty($productId, $qty);
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @param int $summaryQty
+     * @param int $origQty
+     * @return int
+     */
+    public function checkQuoteItemQty($productId, $qty, $summaryQty, $origQty = 0);
+
+    /**
+     * @param int $productId
+     * @param int|null $qty
+     * @return bool
+     */
+    public function verifyStock($productId, $qty = null);
+
+    /**
+     * @param int $productId
+     * @param int|null $qty
+     * @return bool
+     */
+    public function verifyNotification($productId, $qty = null);
+
+    /**
+     * @param int $productId
+     * @return bool
+     */
+    public function getIsInStock($productId);
+
+    /**
+     * @param int $productId
+     * @return int
+     */
+    public function getStockQty($productId);
+
+    /**
+     * @param int $productId
+     * @param int $qty
+     * @return bool
+     */
+    public function checkQtyIncrements($productId, $qty);
+
+    /**
+     * @param int $productTypeId
+     * @return bool
+     */
+    public function isQty($productTypeId);
+
+    /**
+     * @param int|null $filter
+     * @return bool
+     */
+    public function getIsQtyTypeIds($filter = null);
+}
diff --git a/app/code/Magento/CatalogInventory/Service/V1/StockStatusService.php b/app/code/Magento/CatalogInventory/Service/V1/StockStatusService.php
new file mode 100644
index 00000000000..9457bc59849
--- /dev/null
+++ b/app/code/Magento/CatalogInventory/Service/V1/StockStatusService.php
@@ -0,0 +1,54 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogInventory\Service\V1;
+
+use Magento\CatalogInventory\Model\Stock;
+use Magento\CatalogInventory\Model\Stock\Status;
+
+/**
+ * Service related to Product Stock Status
+ */
+class StockStatusService implements StockStatusServiceInterface
+{
+    /**
+     * @var Status
+     */
+    protected $stockStatus;
+
+    /**
+     * @param Status $stockStatus
+     */
+    public function __construct(Status $stockStatus)
+    {
+        $this->stockStatus = $stockStatus;
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function getProductStockStatus($productIds, $websiteId, $stockId = Stock::DEFAULT_STOCK_ID)
+    {
+        return $this->stockStatus->getProductStockStatus($productIds, $websiteId, $stockId);
+    }
+}
diff --git a/app/code/Magento/CatalogInventory/Service/V1/StockStatusServiceInterface.php b/app/code/Magento/CatalogInventory/Service/V1/StockStatusServiceInterface.php
new file mode 100644
index 00000000000..30214e24014
--- /dev/null
+++ b/app/code/Magento/CatalogInventory/Service/V1/StockStatusServiceInterface.php
@@ -0,0 +1,42 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogInventory\Service\V1;
+
+use Magento\CatalogInventory\Model\Stock;
+
+/**
+ * Interface StockStatusServiceInterface
+ */
+interface StockStatusServiceInterface
+{
+    /**
+     * Retrieve Product Stock Status
+     *
+     * @param int[] $productIds
+     * @param int $websiteId
+     * @param int $stockId
+     * @return array
+     */
+    public function getProductStockStatus($productIds, $websiteId, $stockId = Stock::DEFAULT_STOCK_ID);
+}
diff --git a/app/code/Magento/CatalogInventory/etc/di.xml b/app/code/Magento/CatalogInventory/etc/di.xml
index 0548cef5e75..bad18e477cf 100644
--- a/app/code/Magento/CatalogInventory/etc/di.xml
+++ b/app/code/Magento/CatalogInventory/etc/di.xml
@@ -24,6 +24,7 @@
  */
 -->
 <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/ObjectManager/etc/config.xsd">
+    <preference for="Magento\CatalogInventory\Service\V1\StockStatusServiceInterface" type="Magento\CatalogInventory\Service\V1\StockStatusService" />
     <type name="Magento\CatalogInventory\Model\Observer">
         <arguments>
             <argument name="resourceIndexerStock" xsi:type="object">Magento\CatalogInventory\Model\Resource\Indexer\Stock\Proxy</argument>
diff --git a/app/code/Magento/CatalogInventory/etc/module.xml b/app/code/Magento/CatalogInventory/etc/module.xml
index 2cb076739fa..0ba165098ca 100644
--- a/app/code/Magento/CatalogInventory/etc/module.xml
+++ b/app/code/Magento/CatalogInventory/etc/module.xml
@@ -36,7 +36,6 @@
             <module name="Magento_Backend"/>
             <module name="Magento_Index"/>
             <module name="Magento_Sales"/>
-            <module name="Magento_CatalogSearch"/>
             <module name="Magento_Eav"/>
         </depends>
     </module>
diff --git a/app/code/Magento/CatalogInventory/sql/cataloginventory_setup/install-1.6.0.0.php b/app/code/Magento/CatalogInventory/sql/cataloginventory_setup/install-1.6.0.0.php
index 586bffde1ab..a82670d8f83 100644
--- a/app/code/Magento/CatalogInventory/sql/cataloginventory_setup/install-1.6.0.0.php
+++ b/app/code/Magento/CatalogInventory/sql/cataloginventory_setup/install-1.6.0.0.php
@@ -206,9 +206,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('product_id', 'stock_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('cataloginventory_stock_item', array('product_id')),
-    array('product_id')
 )->addIndex(
     $installer->getIdxName('cataloginventory_stock_item', array('stock_id')),
     array('stock_id')
diff --git a/app/code/Magento/CatalogRule/sql/catalogrule_setup/install-1.6.0.0.php b/app/code/Magento/CatalogRule/sql/catalogrule_setup/install-1.6.0.0.php
index 29a17cf8850..224093635db 100644
--- a/app/code/Magento/CatalogRule/sql/catalogrule_setup/install-1.6.0.0.php
+++ b/app/code/Magento/CatalogRule/sql/catalogrule_setup/install-1.6.0.0.php
@@ -205,9 +205,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('rule_id', 'from_time', 'to_time', 'website_id', 'customer_group_id', 'product_id', 'sort_order'),
     array('type' => 'unique')
-)->addIndex(
-    $installer->getIdxName('catalogrule_product', array('rule_id')),
-    array('rule_id')
 )->addIndex(
     $installer->getIdxName('catalogrule_product', array('customer_group_id')),
     array('customer_group_id')
@@ -392,9 +389,6 @@ $table = $installer->getConnection()->newTable(
     null,
     array('unsigned' => true, 'nullable' => false, 'primary' => true, 'default' => '0'),
     'Website Id'
-)->addIndex(
-    $installer->getIdxName('catalogrule_group_website', array('rule_id')),
-    array('rule_id')
 )->addIndex(
     $installer->getIdxName('catalogrule_group_website', array('customer_group_id')),
     array('customer_group_id')
diff --git a/app/code/Magento/CatalogRule/sql/catalogrule_setup/upgrade-1.6.0.1-1.6.0.2.php b/app/code/Magento/CatalogRule/sql/catalogrule_setup/upgrade-1.6.0.1-1.6.0.2.php
index 4f980591bce..6ad7b638b9f 100644
--- a/app/code/Magento/CatalogRule/sql/catalogrule_setup/upgrade-1.6.0.1-1.6.0.2.php
+++ b/app/code/Magento/CatalogRule/sql/catalogrule_setup/upgrade-1.6.0.1-1.6.0.2.php
@@ -52,9 +52,6 @@ if (!$connection->isTableExists($rulesWebsitesTable)) {
         null,
         array('unsigned' => true, 'nullable' => false, 'primary' => true),
         'Website Id'
-    )->addIndex(
-        $installer->getIdxName('catalogrule_website', array('rule_id')),
-        array('rule_id')
     )->addIndex(
         $installer->getIdxName('catalogrule_website', array('website_id')),
         array('website_id')
@@ -98,9 +95,6 @@ if (!$connection->isTableExists($rulesCustomerGroupsTable)) {
         null,
         array('unsigned' => true, 'nullable' => false, 'primary' => true),
         'Customer Group Id'
-    )->addIndex(
-        $installer->getIdxName('catalogrule_customer_group', array('rule_id')),
-        array('rule_id')
     )->addIndex(
         $installer->getIdxName('catalogrule_customer_group', array('customer_group_id')),
         array('customer_group_id')
diff --git a/app/code/Magento/CatalogSearch/Model/Resource/Advanced/Collection.php b/app/code/Magento/CatalogSearch/Model/Resource/Advanced/Collection.php
index 43bd0edab2f..4763a0154ce 100644
--- a/app/code/Magento/CatalogSearch/Model/Resource/Advanced/Collection.php
+++ b/app/code/Magento/CatalogSearch/Model/Resource/Advanced/Collection.php
@@ -143,7 +143,7 @@ class Collection extends \Magento\Catalog\Model\Resource\Product\Collection
                             $select->where('t1.entity_id = price_index.entity_id');
                         }
 
-                        $field = $this->getConnection()->getCheckSql('t2.value_id>0', 't2.value', 't1.value');
+                        $field = $this->getConnection()->getIfNullSql('t2.value', 't1.value');
                     }
 
                     if (is_array($conditionValue)) {
diff --git a/app/code/Magento/CatalogSearch/Model/Resource/Search/Collection.php b/app/code/Magento/CatalogSearch/Model/Resource/Search/Collection.php
index cc5a85470a9..ee15a21acb2 100644
--- a/app/code/Magento/CatalogSearch/Model/Resource/Search/Collection.php
+++ b/app/code/Magento/CatalogSearch/Model/Resource/Search/Collection.php
@@ -226,7 +226,7 @@ class Collection extends \Magento\Catalog\Model\Resource\Product\Collection
             }
         }
 
-        $ifValueId = $this->getConnection()->getCheckSql('t2.value_id > 0', 't2.value', 't1.value');
+        $ifValueId = $this->getConnection()->getIfNullSql('t2.value', 't1.value');
         foreach ($tables as $table => $attributeIds) {
             $selects[] = $this->getConnection()->select()->from(
                 array('t1' => $table),
diff --git a/app/code/Magento/CatalogSearch/sql/catalogsearch_setup/install-1.6.0.0.php b/app/code/Magento/CatalogSearch/sql/catalogsearch_setup/install-1.6.0.0.php
index 6d17ca35113..26d99fb4ba9 100644
--- a/app/code/Magento/CatalogSearch/sql/catalogsearch_setup/install-1.6.0.0.php
+++ b/app/code/Magento/CatalogSearch/sql/catalogsearch_setup/install-1.6.0.0.php
@@ -139,9 +139,6 @@ $table = $installer->getConnection()->newTable(
     '20,4',
     array('nullable' => false, 'default' => '0.0000'),
     'Relevance'
-)->addIndex(
-    $installer->getIdxName('catalogsearch_result', 'query_id'),
-    'query_id'
 )->addForeignKey(
     $installer->getFkName('catalogsearch_result', 'query_id', 'catalogsearch_query', 'query_id'),
     'query_id',
diff --git a/app/code/Magento/Checkout/Block/Success.php b/app/code/Magento/Checkout/Block/Success.php
index b3b0de6753a..ce6bddba54a 100644
--- a/app/code/Magento/Checkout/Block/Success.php
+++ b/app/code/Magento/Checkout/Block/Success.php
@@ -50,7 +50,7 @@ class Success extends \Magento\Framework\View\Element\Template
     public function getRealOrderId()
     {
         /** @var \Magento\Sales\Model\Order $order */
-        $order = $this->_orderFactory()->create()->load($this->getLastOrderId());
+        $order = $this->_orderFactory->create()->load($this->getLastOrderId());
         return $order->getIncrementId();
     }
 }
diff --git a/app/code/Magento/Checkout/Model/Cart.php b/app/code/Magento/Checkout/Model/Cart.php
index 4f52ae5c200..6e08d5989b4 100644
--- a/app/code/Magento/Checkout/Model/Cart.php
+++ b/app/code/Magento/Checkout/Model/Cart.php
@@ -27,8 +27,6 @@ use Magento\Catalog\Model\Product;
 
 /**
  * Shopping cart model
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
 class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\Cart\CartInterface
 {
@@ -51,7 +49,7 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
      *
      * @var \Magento\Framework\Event\ManagerInterface
      */
-    protected $_eventManager = null;
+    protected $_eventManager;
 
     /**
      * Core store config
@@ -90,6 +88,11 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
      */
     protected $messageManager;
 
+    /**
+     * @var \Magento\CatalogInventory\Service\V1\StockItem
+     */
+    protected $stockItemService;
+
     /**
      * @param \Magento\Framework\Event\ManagerInterface $eventManager
      * @param \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig
@@ -99,6 +102,7 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
      * @param Session $checkoutSession
      * @param \Magento\Customer\Model\Session $customerSession
      * @param \Magento\Framework\Message\ManagerInterface $messageManager
+     * @param \Magento\CatalogInventory\Service\V1\StockItem $stockItemService
      * @param array $data
      */
     public function __construct(
@@ -110,6 +114,7 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
         Session $checkoutSession,
         \Magento\Customer\Model\Session $customerSession,
         \Magento\Framework\Message\ManagerInterface $messageManager,
+        \Magento\CatalogInventory\Service\V1\StockItem $stockItemService,
         array $data = array()
     ) {
         $this->_eventManager = $eventManager;
@@ -120,6 +125,7 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
         $this->_checkoutSession = $checkoutSession;
         $this->_customerSession = $customerSession;
         $this->messageManager = $messageManager;
+        $this->stockItemService = $stockItemService;
         parent::__construct($data);
     }
 
@@ -241,11 +247,9 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
     {
         /* @var $orderItem \Magento\Sales\Model\Order\Item */
         if (is_null($orderItem->getParentItem())) {
-            $product = $this->_productFactory->create()->setStoreId(
-                $this->_storeManager->getStore()->getId()
-            )->load(
-                $orderItem->getProductId()
-            );
+            $product = $this->_productFactory->create()
+                ->setStoreId($this->_storeManager->getStore()->getId())
+                ->load($orderItem->getProductId());
             if (!$product->getId()) {
                 return $this;
             }
@@ -276,19 +280,15 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
         if ($productInfo instanceof Product) {
             $product = $productInfo;
         } elseif (is_int($productInfo) || is_string($productInfo)) {
-            $product = $this->_productFactory->create()->setStoreId(
-                $this->_storeManager->getStore()->getId()
-            )->load(
-                $productInfo
-            );
+            $product = $this->_productFactory->create()
+                ->setStoreId($this->_storeManager->getStore()->getId())
+                ->load($productInfo);
         }
         $currentWebsiteId = $this->_storeManager->getStore()->getWebsiteId();
-        if (!$product || !$product->getId() || !is_array(
-            $product->getWebsiteIds()
-        ) || !in_array(
-            $currentWebsiteId,
-            $product->getWebsiteIds()
-        )
+        if (!$product
+            || !$product->getId()
+            || !is_array($product->getWebsiteIds())
+            || !in_array($currentWebsiteId, $product->getWebsiteIds())
         ) {
             throw new \Magento\Framework\Model\Exception(__('We can\'t find the product.'));
         }
@@ -330,15 +330,15 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
     {
         $product = $this->_getProduct($productInfo);
         $request = $this->_getProductRequest($requestInfo);
-
         $productId = $product->getId();
 
-        if ($product->getStockItem()) {
-            $minimumQty = $product->getStockItem()->getMinSaleQty();
+        if ($productId) {
+            $minimumQty = $this->stockItemService->getMinSaleQty($productId);
             //If product was not found in cart and there is set minimal qty for it
-            if ($minimumQty && $minimumQty > 0 && $request->getQty() < $minimumQty && !$this->getQuote()->hasProductId(
-                $productId
-            )
+            if ($minimumQty
+                && $minimumQty > 0
+                && $request->getQty() < $minimumQty
+                && !$this->getQuote()->hasProductId($productId)
             ) {
                 $request->setQty($minimumQty);
             }
@@ -355,10 +355,14 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
              * String we can get if prepare process has error
              */
             if (is_string($result)) {
-                $redirectUrl = $product->hasOptionsValidationFail() ? $product->getUrlModel()->getUrl(
-                    $product,
-                    array('_query' => array('startcustomization' => 1))
-                ) : $product->getProductUrl();
+                if ($product->hasOptionsValidationFail()) {
+                    $redirectUrl = $product->getUrlModel()->getUrl(
+                        $product,
+                        array('_query' => array('startcustomization' => 1))
+                    );
+                } else {
+                    $redirectUrl = $product->getProductUrl();
+                }
                 $this->_checkoutSession->setRedirectUrl($redirectUrl);
                 if ($this->_checkoutSession->getUseNotice() === null) {
                     $this->_checkoutSession->setUseNotice(true);
@@ -390,7 +394,7 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
 
         if (!empty($productIds)) {
             foreach ($productIds as $productId) {
-                $productId = (int)$productId;
+                $productId = (int) $productId;
                 if (!$productId) {
                     continue;
                 }
@@ -432,7 +436,7 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
             if (!isset($itemInfo['qty'])) {
                 continue;
             }
-            $qty = (double)$itemInfo['qty'];
+            $qty = (float) $itemInfo['qty'];
             if ($qty <= 0) {
                 continue;
             }
@@ -447,16 +451,9 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
                 continue;
             }
 
-            /* @var $stockItem \Magento\CatalogInventory\Model\Stock\Item */
-            $stockItem = $product->getStockItem();
-            if (!$stockItem) {
-                continue;
-            }
-
             $data[$itemId]['before_suggest_qty'] = $qty;
-            $data[$itemId]['qty'] = $stockItem->suggestQty($qty);
+            $data[$itemId]['qty'] = $this->stockItemService->suggestQty($product->getId(), $qty);
         }
-
         return $data;
     }
 
@@ -597,16 +594,16 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
         //and get new quote id. This is done for cases when quote was created
         //not by customer (from backend for example).
         if (!$quoteId && $this->_customerSession->isLoggedIn()) {
-            $quote = $this->_checkoutSession->getQuote();
+            $this->_checkoutSession->getQuote();
             $quoteId = $this->_checkoutSession->getQuoteId();
         }
 
         if ($quoteId && $this->_summaryQty === null) {
-            if ($this->_scopeConfig->getValue('checkout/cart_link/use_qty', \Magento\Store\Model\ScopeInterface::SCOPE_STORE)) {
-                $this->_summaryQty = $this->getItemsQty();
-            } else {
-                $this->_summaryQty = $this->getItemsCount();
-            }
+            $useQty = $this->_scopeConfig->getValue(
+                'checkout/cart_link/use_qty',
+                \Magento\Store\Model\ScopeInterface::SCOPE_STORE
+            );
+            $this->_summaryQty = $useQty ? $this->getItemsQty() : $this->getItemsCount();
         }
         return $this->_summaryQty;
     }
@@ -655,13 +652,13 @@ class Cart extends \Magento\Framework\Object implements \Magento\Checkout\Model\
             $product = $this->_getProduct($productId);
             $request = $this->_getProductRequest($requestInfo);
 
-            if ($product->getStockItem()) {
-                $minimumQty = $product->getStockItem()->getMinSaleQty();
+            if ($productId) {
+                $minimumQty = $this->stockItemService->getMinSaleQty($productId);
                 // If product was not found in cart and there is set minimal qty for it
-                if ($minimumQty &&
-                    $minimumQty > 0 &&
-                    $request->getQty() < $minimumQty &&
-                    !$this->getQuote()->hasProductId($productId)
+                if ($minimumQty
+                    && $minimumQty > 0
+                    && $request->getQty() < $minimumQty
+                    && !$this->getQuote()->hasProductId($productId)
                 ) {
                     $request->setQty($minimumQty);
                 }
diff --git a/app/code/Magento/ConfigurableProduct/Block/Stockqty/Type/Configurable.php b/app/code/Magento/ConfigurableProduct/Block/Stockqty/Type/Configurable.php
index 149bf6e6eed..326e092ac19 100644
--- a/app/code/Magento/ConfigurableProduct/Block/Stockqty/Type/Configurable.php
+++ b/app/code/Magento/ConfigurableProduct/Block/Stockqty/Type/Configurable.php
@@ -1,7 +1,5 @@
 <?php
 /**
- * Product stock qty block for configurable product type
- *
  * Magento
  *
  * NOTICE OF LICENSE
@@ -27,6 +25,9 @@ namespace Magento\ConfigurableProduct\Block\Stockqty\Type;
 
 use Magento\Catalog\Model\Product;
 
+/**
+ * Product stock qty block for configurable product type
+ */
 class Configurable extends \Magento\CatalogInventory\Block\Stockqty\Composite
 {
     /**
diff --git a/app/code/Magento/ConfigurableProduct/Model/Product/Type/Configurable.php b/app/code/Magento/ConfigurableProduct/Model/Product/Type/Configurable.php
index a8be0223e6a..62c0296a03e 100644
--- a/app/code/Magento/ConfigurableProduct/Model/Product/Type/Configurable.php
+++ b/app/code/Magento/ConfigurableProduct/Model/Product/Type/Configurable.php
@@ -1,9 +1,5 @@
 <?php
 /**
- * Configurable product type implementation
- *
- * This type builds in product attributes and existing simple products
- *
  * Magento
  *
  * NOTICE OF LICENSE
@@ -28,12 +24,19 @@
 namespace Magento\ConfigurableProduct\Model\Product\Type;
 
 /**
+ * Configurable product type implementation
+ *
+ * This type builds in product attributes and existing simple products
+ *
  * @SuppressWarnings(PHPMD.TooManyFields)
  * @SuppressWarnings(PHPMD.ExcessiveClassComplexity)
  * @SuppressWarnings(PHPMD.CouplingBetweenObjects)
  */
 class Configurable extends \Magento\Catalog\Model\Product\Type\AbstractType
 {
+    /**
+     * Product type code
+     */
     const TYPE_CODE = 'configurable';
 
     /**
@@ -115,8 +118,7 @@ class Configurable extends \Magento\Catalog\Model\Product\Type\AbstractType
     /**
      * Product collection factory
      *
-     * @var
-     * \Magento\ConfigurableProduct\Model\Resource\Product\Type\Configurable\Product\CollectionFactory
+     * @var \Magento\ConfigurableProduct\Model\Resource\Product\Type\Configurable\Product\CollectionFactory
      */
     protected $_productCollectionFactory;
 
diff --git a/app/code/Magento/ConfigurableProduct/sql/configurable_setup/install-1.0.0.0.php b/app/code/Magento/ConfigurableProduct/sql/configurable_setup/install-1.0.0.0.php
index 9ceaad454fc..16fbce94190 100644
--- a/app/code/Magento/ConfigurableProduct/sql/configurable_setup/install-1.0.0.0.php
+++ b/app/code/Magento/ConfigurableProduct/sql/configurable_setup/install-1.0.0.0.php
@@ -57,9 +57,6 @@ $table = $installer->getConnection()->newTable(
     null,
     array('unsigned' => true, 'nullable' => false, 'default' => '0'),
     'Position'
-)->addIndex(
-    $installer->getIdxName('catalog_product_super_attribute', array('product_id')),
-    array('product_id')
 )->addIndex(
     $installer->getIdxName(
         'catalog_product_super_attribute',
@@ -123,9 +120,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('product_super_attribute_id', 'store_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('catalog_product_super_attribute_label', array('product_super_attribute_id')),
-    array('product_super_attribute_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_super_attribute_label', array('store_id')),
     array('store_id')
@@ -194,9 +188,6 @@ $table = $installer->getConnection()->newTable(
     null,
     array('unsigned' => true, 'nullable' => false, 'default' => '0'),
     'Website ID'
-)->addIndex(
-    $installer->getIdxName('catalog_product_super_attribute_pricing', array('product_super_attribute_id')),
-    array('product_super_attribute_id')
 )->addIndex(
     $installer->getIdxName('catalog_product_super_attribute_pricing', array('website_id')),
     array('website_id')
@@ -258,9 +249,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('catalog_product_super_link', array('parent_id')),
     array('parent_id')
-)->addIndex(
-    $installer->getIdxName('catalog_product_super_link', array('product_id')),
-    array('product_id')
 )->addIndex(
     $installer->getIdxName(
         'catalog_product_super_link',
diff --git a/app/code/Magento/ConfigurableProduct/view/adminhtml/templates/catalog/product/edit/super/config.phtml b/app/code/Magento/ConfigurableProduct/view/adminhtml/templates/catalog/product/edit/super/config.phtml
index 4a0c3cb1292..0d125411ceb 100644
--- a/app/code/Magento/ConfigurableProduct/view/adminhtml/templates/catalog/product/edit/super/config.phtml
+++ b/app/code/Magento/ConfigurableProduct/view/adminhtml/templates/catalog/product/edit/super/config.phtml
@@ -66,7 +66,7 @@ jQuery(function($) {
         collapsableArea = $('> .collapse', collapsableWrapper),
         stockAvailabilityField = $('#quantity_and_stock_status'),
         qtyField = $('#qty'),
-        currentProductTemplateControl = $('#product-template-suggest-container .actions-split > .action-toggle'),
+        currentProductTemplateControl = $('#product-template-suggest-container .action-dropdown > .action-toggle'),
         attributesInput = $("input[name='attributes[]']", variationsContainer),
         hasVariations = <?php echo ($this->getProduct()->getTypeId() == Configurable::TYPE_CODE || $this->getRequest()->has('attributes')) ? 'true' : 'false' ?>,
         isLocked = function (element) {
diff --git a/app/code/Magento/ConfigurableProduct/view/adminhtml/web/product/product.css b/app/code/Magento/ConfigurableProduct/view/adminhtml/web/product/product.css
index 213e7b4b5ef..28580006915 100644
--- a/app/code/Magento/ConfigurableProduct/view/adminhtml/web/product/product.css
+++ b/app/code/Magento/ConfigurableProduct/view/adminhtml/web/product/product.css
@@ -238,6 +238,12 @@
     vertical-align: top;
 }
 
+#product_options_container .data-table td.opt-price-type,
+#product_options_container .data-table td.select-opt-price-type,
+#product_options_container .data-table td.select-opt-price{
+    width: 13%;
+}
+
 #product_options_container .product-option-scope-checkbox {
     margin: 10px 5px 10px 0;
 }
diff --git a/app/code/Magento/Core/sql/core_setup/install-1.6.0.0.php b/app/code/Magento/Core/sql/core_setup/install-1.6.0.0.php
index 77c93c040b0..c3701b869e5 100644
--- a/app/code/Magento/Core/sql/core_setup/install-1.6.0.0.php
+++ b/app/code/Magento/Core/sql/core_setup/install-1.6.0.0.php
@@ -423,9 +423,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('variable_id', 'store_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('core_variable_value', array('variable_id')),
-    array('variable_id')
 )->addIndex(
     $installer->getIdxName('core_variable_value', array('store_id')),
     array('store_id')
diff --git a/app/code/Magento/Customer/sql/customer_setup/install-1.6.0.0.php b/app/code/Magento/Customer/sql/customer_setup/install-1.6.0.0.php
index 87daf880e80..affc7f0b4f7 100644
--- a/app/code/Magento/Customer/sql/customer_setup/install-1.6.0.0.php
+++ b/app/code/Magento/Customer/sql/customer_setup/install-1.6.0.0.php
@@ -245,9 +245,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('customer_address_entity_datetime', array('attribute_id')),
     array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('customer_address_entity_datetime', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('customer_address_entity_datetime', array('entity_id', 'attribute_id', 'value')),
     array('entity_id', 'attribute_id', 'value')
@@ -326,9 +323,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('customer_address_entity_decimal', array('attribute_id')),
     array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('customer_address_entity_decimal', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('customer_address_entity_decimal', array('entity_id', 'attribute_id', 'value')),
     array('entity_id', 'attribute_id', 'value')
@@ -407,9 +401,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('customer_address_entity_int', array('attribute_id')),
     array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('customer_address_entity_int', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('customer_address_entity_int', array('entity_id', 'attribute_id', 'value')),
     array('entity_id', 'attribute_id', 'value')
@@ -488,9 +479,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('customer_address_entity_text', array('attribute_id')),
     array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('customer_address_entity_text', array('entity_id')),
-    array('entity_id')
 )->addForeignKey(
     $installer->getFkName('customer_address_entity_text', 'attribute_id', 'eav_attribute', 'attribute_id'),
     'attribute_id',
@@ -566,9 +554,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('customer_address_entity_varchar', array('attribute_id')),
     array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('customer_address_entity_varchar', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('customer_address_entity_varchar', array('entity_id', 'attribute_id', 'value')),
     array('entity_id', 'attribute_id', 'value')
@@ -647,9 +632,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('customer_entity_datetime', array('attribute_id')),
     array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('customer_entity_datetime', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('customer_entity_datetime', array('entity_id', 'attribute_id', 'value')),
     array('entity_id', 'attribute_id', 'value')
@@ -728,9 +710,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('customer_entity_decimal', array('attribute_id')),
     array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('customer_entity_decimal', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('customer_entity_decimal', array('entity_id', 'attribute_id', 'value')),
     array('entity_id', 'attribute_id', 'value')
@@ -809,9 +788,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('customer_entity_int', array('attribute_id')),
     array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('customer_entity_int', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('customer_entity_int', array('entity_id', 'attribute_id', 'value')),
     array('entity_id', 'attribute_id', 'value')
@@ -890,9 +866,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('customer_entity_text', array('attribute_id')),
     array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('customer_entity_text', array('entity_id')),
-    array('entity_id')
 )->addForeignKey(
     $installer->getFkName('customer_entity_text', 'attribute_id', 'eav_attribute', 'attribute_id'),
     'attribute_id',
@@ -968,9 +941,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('customer_entity_varchar', array('attribute_id')),
     array('attribute_id')
-)->addIndex(
-    $installer->getIdxName('customer_entity_varchar', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('customer_entity_varchar', array('entity_id', 'attribute_id', 'value')),
     array('entity_id', 'attribute_id', 'value')
diff --git a/app/code/Magento/Downloadable/sql/downloadable_setup/install-1.6.0.0.php b/app/code/Magento/Downloadable/sql/downloadable_setup/install-1.6.0.0.php
index c156aa79a1f..8f1a552ea96 100644
--- a/app/code/Magento/Downloadable/sql/downloadable_setup/install-1.6.0.0.php
+++ b/app/code/Magento/Downloadable/sql/downloadable_setup/install-1.6.0.0.php
@@ -98,9 +98,6 @@ $table = $installer->getConnection()->newTable(
     20,
     array(),
     'Sample Type'
-)->addIndex(
-    $installer->getIdxName('downloadable_link', 'product_id'),
-    'product_id'
 )->addIndex(
     $installer->getIdxName('downloadable_link', array('product_id', 'sort_order')),
     array('product_id', 'sort_order')
@@ -434,9 +431,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('link_id', 'store_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('downloadable_link_title', 'link_id'),
-    'link_id'
 )->addForeignKey(
     $installer->getFkName('downloadable_link_title', 'link_id', 'downloadable_link', 'link_id'),
     'link_id',
@@ -552,9 +546,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('sample_id', 'store_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('downloadable_sample_title', 'sample_id'),
-    'sample_id'
 )->addForeignKey(
     $installer->getFkName('downloadable_sample_title', 'sample_id', 'downloadable_sample', 'sample_id'),
     'sample_id',
diff --git a/app/code/Magento/Downloadable/view/adminhtml/templates/product/edit/downloadable/links.phtml b/app/code/Magento/Downloadable/view/adminhtml/templates/product/edit/downloadable/links.phtml
index c34826f1174..f68b388ba10 100644
--- a/app/code/Magento/Downloadable/view/adminhtml/templates/product/edit/downloadable/links.phtml
+++ b/app/code/Magento/Downloadable/view/adminhtml/templates/product/edit/downloadable/links.phtml
@@ -119,7 +119,7 @@ var linkTemplate = '<tr>'+
         '<div class="files">'+
             '<div class="row">'+
                 '<label for="downloadable_link_{{id}}_sample_file_type"><input type="radio" class="radio" id="downloadable_link_{{id}}_sample_file_type" name="downloadable[link][{{id}}][sample][type]" value="file"{{sample_file_checked}} /> File:</label>'+
-                '<input type="hidden" id="downloadable_link_{{id}}_sample_file_save" name="downloadable[link][{{id}}][sample][file]" value="{{sample_file_save}}" />'+
+                '<input type="hidden" id="downloadable_link_{{id}}_sample_file_save" name="downloadable[link][{{id}}][sample][file]" value="{{sample_file_save}}" class="validate-downloadable-file"/>'+
                 '<div id="downloadable_link_{{id}}_sample_file" class="uploader">'+
                     '<div id="downloadable_link_{{id}}_sample_file-old" class="file-row-info"></div>'+
                     '<div id="downloadable_link_{{id}}_sample_file-new" class="file-row-info"></div>'+
@@ -136,7 +136,7 @@ var linkTemplate = '<tr>'+
                 '</div>'+
             '</div>'+
             '<div class="row">'+
-                '<label for="downloadable_link_{{id}}_sample_url_type"><input type="radio" class="radio" id="downloadable_link_{{id}}_sample_url_type" name="downloadable[link][{{id}}][sample][type]" value="url"{{sample_url_checked}} /> URL:</label><input type="text" class="input-text" name="downloadable[link][{{id}}][sample][url]" value="{{sample_url}}" />'+
+                '<label for="downloadable_link_{{id}}_sample_url_type"><input type="radio" class="radio" id="downloadable_link_{{id}}_sample_url_type" name="downloadable[link][{{id}}][sample][type]" value="url"{{sample_url_checked}} /> URL:</label><input type="text" class="input-text validate-downloadable-url" name="downloadable[link][{{id}}][sample][url]" value="{{sample_url}}" />'+
             '</div>'+
             '<div>'+
                 '<span id="downloadable_link_{{id}}_sample_container"></span>'+
diff --git a/app/code/Magento/Downloadable/view/adminhtml/web/product/validation-rules.js b/app/code/Magento/Downloadable/view/adminhtml/web/product/validation-rules.js
index dca69fa81a5..94775b7207c 100644
--- a/app/code/Magento/Downloadable/view/adminhtml/web/product/validation-rules.js
+++ b/app/code/Magento/Downloadable/view/adminhtml/web/product/validation-rules.js
@@ -24,7 +24,7 @@
  */
 /*global newFileContainer:true, alertAlreadyDisplayed:true, alert:true, linkType:true*/
 (function ($) {
-    $.validator.addMethod('validate-downloadable-file', function(v,element) {
+    $.validator.addMethod('validate-downloadable-file', function (v, element) {
         var elmParent = $(element).parent(),
             linkType = elmParent.find('input[value="file"]');
         if (linkType.is(':checked') && (v === '' || v === '[]')) {
@@ -32,30 +32,18 @@
             if (!alertAlreadyDisplayed && (newFileContainer.empty() || newFileContainer.is(':visible'))) {
                 alertAlreadyDisplayed = true;
                 alert($.mage.__('There are files that were selected but not uploaded yet. ' +
-                    'Please upload or remove them first'));
+                    'Please upload or remove them first')
+                );
             }
             return false;
         }
         return true;
     }, 'Please upload a file.');
-    $.validator.addMethod('validate-downloadable-url', function(v,element) {
-        linkType = $(element).parent().find('input[value="file"]');
+    $.validator.addMethod('validate-downloadable-url', function (v, element) {
+        linkType = $(element).parent().find('input[value="url"]');
         if (linkType.is(':checked') && v === '') {
             return false;
         }
         return true;
     }, 'Please specify Url.');
-    $.validator.addMethod('validate-downloadable-link-sample-file', function(v,element) {
-        var fileSaveElm = $(element).closest('div').next('input[type="hidden"]');
-        if ($(element).is(':checked') && (fileSaveElm.val() === '' || fileSaveElm.val() === '[]')) {
-            return false;
-        }
-        return true;
-    }, 'Please specify File.');
-    $.validator.addMethod('validate-downloadable-link-sample-url', function(v,element) {
-        if ($(element).is(':checked') && $(element).closest('p').find('input[type="text"]').val() === '') {
-            return false;
-        }
-        return true;
-    }, 'Please specify Sample URL.');
 })(jQuery);
diff --git a/app/code/Magento/Eav/Model/Entity/Attribute/Backend/AbstractBackend.php b/app/code/Magento/Eav/Model/Entity/Attribute/Backend/AbstractBackend.php
index 0c0e10014b7..373add3c046 100644
--- a/app/code/Magento/Eav/Model/Entity/Attribute/Backend/AbstractBackend.php
+++ b/app/code/Magento/Eav/Model/Entity/Attribute/Backend/AbstractBackend.php
@@ -246,22 +246,23 @@ abstract class AbstractBackend implements \Magento\Eav\Model\Entity\Attribute\Ba
      */
     public function validate($object)
     {
-        $attrCode = $this->getAttribute()->getAttributeCode();
+        $attribute = $this->getAttribute();
+        $attrCode = $attribute->getAttributeCode();
         $value = $object->getData($attrCode);
-        if ($this->getAttribute()->getIsRequired() && $this->getAttribute()->isValueEmpty($value)) {
-            return false;
+        if ($attribute->getIsVisible() && $attribute->getIsRequired() && $attribute->isValueEmpty($value)) {
+            throw new \Magento\Eav\Exception(__('The value of attribute "%1" must be set', $attrCode));
         }
 
-        if ($this->getAttribute()->getIsUnique()
-            && !$this->getAttribute()->getIsRequired()
-            && ($value == '' || $this->getAttribute()->isValueEmpty($value))
+        if ($attribute->getIsUnique()
+            && !$attribute->getIsRequired()
+            && ($value == '' || $attribute->isValueEmpty($value))
         ) {
             return true;
         }
 
-        if ($this->getAttribute()->getIsUnique()) {
-            if (!$this->getAttribute()->getEntity()->checkAttributeUniqueValue($this->getAttribute(), $object)) {
-                $label = $this->getAttribute()->getFrontend()->getLabel();
+        if ($attribute->getIsUnique()) {
+            if (!$attribute->getEntity()->checkAttributeUniqueValue($attribute, $object)) {
+                $label = $attribute->getFrontend()->getLabel();
                 throw new \Magento\Eav\Exception(__('The value of attribute "%1" must be unique', $label));
             }
         }
diff --git a/app/code/Magento/Eav/sql/eav_setup/install-1.6.0.0.php b/app/code/Magento/Eav/sql/eav_setup/install-1.6.0.0.php
index 4cc4e16fbb9..b903a3ccab3 100644
--- a/app/code/Magento/Eav/sql/eav_setup/install-1.6.0.0.php
+++ b/app/code/Magento/Eav/sql/eav_setup/install-1.6.0.0.php
@@ -261,18 +261,9 @@ $table = $installer->getConnection()->newTable(
     null,
     array('nullable' => true, 'default' => null),
     'Attribute Value'
-)->addIndex(
-    $installer->getIdxName('eav_entity_datetime', array('entity_type_id')),
-    array('entity_type_id')
-)->addIndex(
-    $installer->getIdxName('eav_entity_datetime', array('attribute_id')),
-    array('attribute_id')
 )->addIndex(
     $installer->getIdxName('eav_entity_datetime', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('eav_entity_datetime', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('eav_entity_datetime', array('attribute_id', 'value')),
     array('attribute_id', 'value')
@@ -354,18 +345,9 @@ $table = $installer->getConnection()->newTable(
     '12,4',
     array('nullable' => false, 'default' => '0.0000'),
     'Attribute Value'
-)->addIndex(
-    $installer->getIdxName('eav_entity_decimal', array('entity_type_id')),
-    array('entity_type_id')
-)->addIndex(
-    $installer->getIdxName('eav_entity_decimal', array('attribute_id')),
-    array('attribute_id')
 )->addIndex(
     $installer->getIdxName('eav_entity_decimal', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('eav_entity_decimal', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('eav_entity_decimal', array('attribute_id', 'value')),
     array('attribute_id', 'value')
@@ -447,18 +429,9 @@ $table = $installer->getConnection()->newTable(
     null,
     array('nullable' => false, 'default' => '0'),
     'Attribute Value'
-)->addIndex(
-    $installer->getIdxName('eav_entity_int', array('entity_type_id')),
-    array('entity_type_id')
-)->addIndex(
-    $installer->getIdxName('eav_entity_int', array('attribute_id')),
-    array('attribute_id')
 )->addIndex(
     $installer->getIdxName('eav_entity_int', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('eav_entity_int', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('eav_entity_int', array('attribute_id', 'value')),
     array('attribute_id', 'value')
@@ -549,9 +522,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('eav_entity_text', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('eav_entity_text', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName(
         'eav_entity_text',
@@ -627,18 +597,9 @@ $table = $installer->getConnection()->newTable(
     255,
     array('nullable' => true, 'default' => null),
     'Attribute Value'
-)->addIndex(
-    $installer->getIdxName('eav_entity_varchar', array('entity_type_id')),
-    array('entity_type_id')
-)->addIndex(
-    $installer->getIdxName('eav_entity_varchar', array('attribute_id')),
-    array('attribute_id')
 )->addIndex(
     $installer->getIdxName('eav_entity_varchar', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('eav_entity_varchar', array('entity_id')),
-    array('entity_id')
 )->addIndex(
     $installer->getIdxName('eav_entity_varchar', array('attribute_id', 'value')),
     array('attribute_id', 'value')
@@ -794,12 +755,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('entity_type_id', 'attribute_code'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('eav_attribute', array('entity_type_id')),
-    array('entity_type_id')
-)->addIndex(
-    $installer->getIdxName('eav_attribute', array('entity_type_id')),
-    array('entity_type_id')
 )->addForeignKey(
     $installer->getFkName('eav_attribute', 'entity_type_id', 'eav_entity_type', 'entity_type_id'),
     'entity_type_id',
@@ -1185,9 +1140,6 @@ $table = $installer->getConnection()->newTable(
     255,
     array('nullable' => true, 'default' => null),
     'Value'
-)->addIndex(
-    $installer->getIdxName('eav_attribute_label', array('attribute_id')),
-    array('attribute_id')
 )->addIndex(
     $installer->getIdxName('eav_attribute_label', array('store_id')),
     array('store_id')
@@ -1353,9 +1305,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('type_id', 'code'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('eav_form_fieldset', array('type_id')),
-    array('type_id')
 )->addForeignKey(
     $installer->getFkName('eav_form_fieldset', 'type_id', 'eav_form_type', 'type_id'),
     'type_id',
@@ -1391,9 +1340,6 @@ $table = $installer->getConnection()->newTable(
     255,
     array('nullable' => false),
     'Label'
-)->addIndex(
-    $installer->getIdxName('eav_form_fieldset_label', array('fieldset_id')),
-    array('fieldset_id')
 )->addIndex(
     $installer->getIdxName('eav_form_fieldset_label', array('store_id')),
     array('store_id')
@@ -1459,9 +1405,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('type_id', 'attribute_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('eav_form_element', array('type_id')),
-    array('type_id')
 )->addIndex(
     $installer->getIdxName('eav_form_element', array('fieldset_id')),
     array('fieldset_id')
diff --git a/app/code/Magento/GoogleOptimizer/sql/googleoptimizer_setup/install-2.0.0.0.php b/app/code/Magento/GoogleOptimizer/sql/googleoptimizer_setup/install-2.0.0.0.php
index 5cb70e9da4c..cec2e5a5bc6 100644
--- a/app/code/Magento/GoogleOptimizer/sql/googleoptimizer_setup/install-2.0.0.0.php
+++ b/app/code/Magento/GoogleOptimizer/sql/googleoptimizer_setup/install-2.0.0.0.php
@@ -63,9 +63,6 @@ $table = $installer->getConnection()->newTable(
     '64k',
     array(),
     'Google experiment script'
-)->addIndex(
-    $installer->getIdxName('googleoptimizer_code', array('store_id')),
-    array('store_id')
 )->addIndex(
     $installer->getIdxName(
         'googleoptimizer_code',
diff --git a/app/code/Magento/GroupedProduct/Block/Stockqty/Type/Grouped.php b/app/code/Magento/GroupedProduct/Block/Stockqty/Type/Grouped.php
index f15bf6f8540..5261bf46f5e 100644
--- a/app/code/Magento/GroupedProduct/Block/Stockqty/Type/Grouped.php
+++ b/app/code/Magento/GroupedProduct/Block/Stockqty/Type/Grouped.php
@@ -1,7 +1,5 @@
 <?php
 /**
- * Product stock qty block for grouped product type
- *
  * Magento
  *
  * NOTICE OF LICENSE
@@ -25,8 +23,12 @@
  */
 namespace Magento\GroupedProduct\Block\Stockqty\Type;
 
-class Grouped extends \Magento\CatalogInventory\Block\Stockqty\Composite implements
-    \Magento\Framework\View\Block\IdentityInterface
+use Magento\Framework\View\Block\IdentityInterface;
+
+/**
+ * Product stock qty block for grouped product type
+ */
+class Grouped extends \Magento\CatalogInventory\Block\Stockqty\Composite implements IdentityInterface
 {
     /**
      * Retrieve child products
diff --git a/app/code/Magento/ImportExport/Model/Import/Entity/Product.php b/app/code/Magento/ImportExport/Model/Import/Entity/Product.php
index 41d7fb2ba01..c3df73de556 100644
--- a/app/code/Magento/ImportExport/Model/Import/Entity/Product.php
+++ b/app/code/Magento/ImportExport/Model/Import/Entity/Product.php
@@ -360,11 +360,9 @@ class Product extends \Magento\ImportExport\Model\Import\Entity\AbstractEntity
     protected $_catalogData = null;
 
     /**
-     * Catalog inventory data
-     *
-     * @var \Magento\CatalogInventory\Helper\Data
+     * @var \Magento\CatalogInventory\Service\V1\StockItem
      */
-    protected $_catalogInventoryData = null;
+    protected $stockItemService;
 
     /**
      * Core event manager proxy
@@ -472,17 +470,17 @@ class Product extends \Magento\ImportExport\Model\Import\Entity\AbstractEntity
      * @param \Magento\ImportExport\Model\Resource\Helper $resourceHelper
      * @param \Magento\Framework\Stdlib\String $string
      * @param \Magento\Framework\Event\ManagerInterface $eventManager
-     * @param \Magento\CatalogInventory\Helper\Data $catalogInventoryData
+     * @param \Magento\CatalogInventory\Service\V1\StockItem $stockItemService
      * @param \Magento\Catalog\Helper\Data $catalogData
      * @param \Magento\ImportExport\Model\Import\Config $importConfig
      * @param \Magento\ImportExport\Model\Import\Proxy\Product\ResourceFactory $resourceFactory
-     * @param \Magento\ImportExport\Model\Import\Entity\Product\OptionFactory $optionFactory
+     * @param Product\OptionFactory $optionFactory
      * @param \Magento\Eav\Model\Resource\Entity\Attribute\Set\CollectionFactory $setColFactory
      * @param \Magento\Catalog\Model\Resource\Category\CollectionFactory $categoryColFactory
      * @param \Magento\Customer\Service\V1\CustomerGroupServiceInterface $customerGroupService
      * @param \Magento\Catalog\Model\ProductFactory $productFactory
      * @param \Magento\Store\Model\StoreManagerInterface $storeManager
-     * @param \Magento\ImportExport\Model\Import\Entity\Product\Type\Factory $productTypeFactory
+     * @param Product\Type\Factory $productTypeFactory
      * @param \Magento\Catalog\Model\Resource\Product\LinkFactory $linkFactory
      * @param \Magento\ImportExport\Model\Import\Proxy\ProductFactory $proxyProdFactory
      * @param \Magento\ImportExport\Model\Import\UploaderFactory $uploaderFactory
@@ -503,7 +501,7 @@ class Product extends \Magento\ImportExport\Model\Import\Entity\AbstractEntity
         \Magento\ImportExport\Model\Resource\Helper $resourceHelper,
         \Magento\Framework\Stdlib\String $string,
         \Magento\Framework\Event\ManagerInterface $eventManager,
-        \Magento\CatalogInventory\Helper\Data $catalogInventoryData,
+        \Magento\CatalogInventory\Service\V1\StockItem $stockItemService,
         \Magento\Catalog\Helper\Data $catalogData,
         \Magento\ImportExport\Model\Import\Config $importConfig,
         \Magento\ImportExport\Model\Import\Proxy\Product\ResourceFactory $resourceFactory,
@@ -526,7 +524,7 @@ class Product extends \Magento\ImportExport\Model\Import\Entity\AbstractEntity
         array $data = array()
     ) {
         $this->_eventManager = $eventManager;
-        $this->_catalogInventoryData = $catalogInventoryData;
+        $this->stockItemService = $stockItemService;
         $this->_catalogData = $catalogData;
         $this->_importConfig = $importConfig;
         $this->_resourceFactory = $resourceFactory;
@@ -1787,7 +1785,7 @@ class Product extends \Magento\ImportExport\Model\Import\Entity\AbstractEntity
 
                 $stockItem->setData($row);
 
-                if ($this->_catalogInventoryData->isQty($this->_newSku[$rowData[self::COL_SKU]]['type_id'])) {
+                if ($this->stockItemService->isQty($this->_newSku[$rowData[self::COL_SKU]]['type_id'])) {
                     if ($stockItem->verifyNotification()) {
                         $stockItem->setLowStockDate(
                             $this->_localeDate->date(
diff --git a/app/code/Magento/Install/Model/Installer/Console.php b/app/code/Magento/Install/Model/Installer/Console.php
index b1f8a29b7f1..4016b8f1a7b 100644
--- a/app/code/Magento/Install/Model/Installer/Console.php
+++ b/app/code/Magento/Install/Model/Installer/Console.php
@@ -190,7 +190,7 @@ class Console extends \Magento\Install\Model\Installer\AbstractInstaller
      * Retrieve validated installation options
      *
      * @param array $options
-     * @return array|false
+     * @return array|bool
      */
     protected function _getInstallOptions(array $options)
     {
@@ -346,6 +346,11 @@ class Console extends \Magento\Install\Model\Installer\AbstractInstaller
                 ]
             );
 
+            $this->checkServer();
+            if ($this->hasErrors()) {
+                return false;
+            }
+
             $installer = $this->_getInstaller();
 
             /**
@@ -548,4 +553,28 @@ class Console extends \Magento\Install\Model\Installer\AbstractInstaller
     {
         return $this->optionalParameters;
     }
+
+    /**
+     * Check if server is applicable for Magento
+     * @return $this
+     */
+    public function checkServer()
+    {
+        \Magento\Framework\Phrase::setRenderer(
+            $this->_objectManager->get('Magento\Framework\Phrase\RendererInterface')
+        );
+
+        $installer = $this->_getInstaller();
+        $result = $installer->checkServer();
+        if (!$result) {
+            /** @var \Magento\Framework\Message\ManagerInterface $messageManager*/
+            $messageManager = $this->_objectManager->get('Magento\Framework\Message\ManagerInterface');
+            /** @var \Magento\Framework\Message\MessageInterface $message */
+            foreach ($messageManager->getMessages()->getItems() as $message) {
+                $this->addError($message->toString());
+            }
+        }
+
+        return $this;
+    }
 }
diff --git a/app/code/Magento/Newsletter/sql/newsletter_setup/install-1.6.0.0.php b/app/code/Magento/Newsletter/sql/newsletter_setup/install-1.6.0.0.php
index a25980eb5d2..59d6bb8da52 100644
--- a/app/code/Magento/Newsletter/sql/newsletter_setup/install-1.6.0.0.php
+++ b/app/code/Magento/Newsletter/sql/newsletter_setup/install-1.6.0.0.php
@@ -307,9 +307,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('newsletter_queue_link', array('subscriber_id')),
     array('subscriber_id')
-)->addIndex(
-    $installer->getIdxName('newsletter_queue_link', array('queue_id')),
-    array('queue_id')
 )->addIndex(
     $installer->getIdxName('newsletter_queue_link', array('queue_id', 'letter_sent_at')),
     array('queue_id', 'letter_sent_at')
diff --git a/app/code/Magento/Payment/Model/Method/AbstractMethod.php b/app/code/Magento/Payment/Model/Method/AbstractMethod.php
index 720776229f0..c5a5761b002 100644
--- a/app/code/Magento/Payment/Model/Method/AbstractMethod.php
+++ b/app/code/Magento/Payment/Model/Method/AbstractMethod.php
@@ -117,6 +117,13 @@ abstract class AbstractMethod extends \Magento\Framework\Object implements Metho
      */
     protected $_canCapturePartial = false;
 
+    /**
+     * Payment Method feature
+     *
+     * @var bool
+     */
+    protected $_canCaptureOnce = false;
+
     /**
      * Payment Method feature
      *
@@ -278,6 +285,16 @@ abstract class AbstractMethod extends \Magento\Framework\Object implements Metho
         return $this->_canCapturePartial;
     }
 
+    /**
+     * Check whether capture can be performed once and no further capture possible
+     *
+     * @return bool
+     */
+    public function canCaptureOnce()
+    {
+        return $this->_canCaptureOnce;
+    }
+
     /**
      * Check refund availability
      *
diff --git a/app/code/Magento/Paypal/Controller/Express/AbstractExpress.php b/app/code/Magento/Paypal/Controller/Express/AbstractExpress.php
index 4f58a271511..3c96bea4692 100644
--- a/app/code/Magento/Paypal/Controller/Express/AbstractExpress.php
+++ b/app/code/Magento/Paypal/Controller/Express/AbstractExpress.php
@@ -238,6 +238,7 @@ abstract class AbstractExpress extends AppAction implements RedirectLoginInterfa
             // TODO verify if this logic of order cancellation is deprecated
             // if there is an order - cancel it
             $orderId = $this->_getCheckoutSession()->getLastOrderId();
+            /** @var \Magento\Sales\Model\Order $order */
             $order = $orderId ? $this->_orderFactory->create()->load($orderId) : false;
             if ($order && $order->getId() && $order->getQuoteId() == $this->_getCheckoutSession()->getQuoteId()) {
                 $order->cancel()->save();
diff --git a/app/code/Magento/Reports/Model/Resource/Event.php b/app/code/Magento/Reports/Model/Resource/Event.php
index c42d00e7111..abf1d6a31a1 100644
--- a/app/code/Magento/Reports/Model/Resource/Event.php
+++ b/app/code/Magento/Reports/Model/Resource/Event.php
@@ -21,15 +21,11 @@
  * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
-
+namespace Magento\Reports\Model\Resource;
 
 /**
  * Report events resource model
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
-namespace Magento\Reports\Model\Resource;
-
 class Event extends \Magento\Framework\Model\Resource\Db\AbstractDb
 {
     /**
@@ -83,8 +79,8 @@ class Event extends \Magento\Framework\Model\Resource\Db\AbstractDb
         if ($types) {
             $this->_getWriteAdapter()->update(
                 $this->getMainTable(),
-                array('subject_id' => (int)$customerId, 'subtype' => 0),
-                array('subject_id = ?' => (int)$visitorId, 'subtype = ?' => 1, 'event_type_id IN(?)' => $types)
+                array('subject_id' => (int) $customerId, 'subtype' => 0),
+                array('subject_id = ?' => (int) $visitorId, 'subtype = ?' => 1, 'event_type_id IN(?)' => $types)
             );
         }
         return $this;
@@ -111,28 +107,21 @@ class Event extends \Magento\Framework\Model\Resource\Db\AbstractDb
     ) {
         $idFieldName = $collection->getResource()->getIdFieldName();
 
-        $derivedSelect = $this->getReadConnection()->select()->from(
-            $this->getTable('report_event'),
-            array('event_id' => new \Zend_Db_Expr('MAX(event_id)'), 'object_id')
-        )->where(
-            'event_type_id = ?',
-            (int)$eventTypeId
-        )->where(
-            'subject_id = ?',
-            (int)$eventSubjectId
-        )->where(
-            'subtype = ?',
-            (int)$subtype
-        )->where(
-            'store_id IN(?)',
-            $this->getCurrentStoreIds()
-        )->group(
-            'object_id'
-        );
+        $derivedSelect = $this->getReadConnection()
+            ->select()
+            ->from(
+                $this->getTable('report_event'),
+                array('event_id' => new \Zend_Db_Expr('MAX(event_id)'), 'object_id')
+            )
+            ->where('event_type_id = ?', (int) $eventTypeId)
+            ->where('subject_id = ?', (int) $eventSubjectId)
+            ->where('subtype = ?', (int) $subtype)
+            ->where('store_id IN(?)', $this->getCurrentStoreIds())
+            ->group('object_id');
 
         if ($skipIds) {
             if (!is_array($skipIds)) {
-                $skipIds = array((int)$skipIds);
+                $skipIds = array((int) $skipIds);
             }
             $derivedSelect->where('object_id NOT IN(?)', $skipIds);
         }
@@ -141,9 +130,7 @@ class Event extends \Magento\Framework\Model\Resource\Db\AbstractDb
             array('evt' => new \Zend_Db_Expr("({$derivedSelect})")),
             "{$idFieldName} = evt.object_id",
             array()
-        )->order(
-            'evt.event_id ' . \Magento\Framework\DB\Select::SQL_DESC
-        );
+        )->order('evt.event_id ' . \Magento\Framework\DB\Select::SQL_DESC);
 
         return $this;
     }
@@ -168,10 +155,11 @@ class Event extends \Magento\Framework\Model\Resource\Db\AbstractDb
             }
         } else {
             // get all stores, required by configuration in current store scope
-            switch ($this->_scopeConfig->getValue(
+            $productsScope = $this->_scopeConfig->getValue(
                 'catalog/recently_products/scope',
                 \Magento\Store\Model\ScopeInterface::SCOPE_STORE
-            )) {
+            );
+            switch ($productsScope) {
                 case 'website':
                     $resourceStore = $this->_storeManager->getStore()->getWebsite()->getStores();
                     break;
@@ -188,7 +176,7 @@ class Event extends \Magento\Framework\Model\Resource\Db\AbstractDb
             }
         }
         foreach ($stores as $key => $store) {
-            $stores[$key] = (int)$store;
+            $stores[$key] = (int) $store;
         }
 
         return $stores;
@@ -210,14 +198,9 @@ class Event extends \Magento\Framework\Model\Resource\Db\AbstractDb
                 array('visitor_table' => $this->getTable('log_visitor')),
                 'event_table.subject_id = visitor_table.visitor_id',
                 array()
-            )->where(
-                'visitor_table.visitor_id IS NULL'
-            )->where(
-                'event_table.subtype = ?',
-                1
-            )->limit(
-                1000
-            );
+            )->where('visitor_table.visitor_id IS NULL')
+                ->where('event_table.subtype = ?', 1)
+                ->limit(1000);
             $eventIds = $this->_getReadAdapter()->fetchCol($select);
 
             if (!$eventIds) {
diff --git a/app/code/Magento/Reports/Model/Resource/Product/Lowstock/Collection.php b/app/code/Magento/Reports/Model/Resource/Product/Lowstock/Collection.php
index 437d6673d94..7989688d704 100644
--- a/app/code/Magento/Reports/Model/Resource/Product/Lowstock/Collection.php
+++ b/app/code/Magento/Reports/Model/Resource/Product/Lowstock/Collection.php
@@ -47,11 +47,9 @@ class Collection extends \Magento\Reports\Model\Resource\Product\Collection
     protected $_inventoryItemTableAlias = 'lowstock_inventory_item';
 
     /**
-     * Catalog inventory data
-     *
-     * @var \Magento\CatalogInventory\Helper\Data
+     * @var \Magento\CatalogInventory\Service\V1\StockItem
      */
-    protected $_inventoryData = null;
+    protected $stockItemService;
 
     /**
      * @var \Magento\CatalogInventory\Model\Resource\Stock\Item
@@ -80,10 +78,10 @@ class Collection extends \Magento\Reports\Model\Resource\Product\Collection
      * @param \Magento\Catalog\Model\Resource\Product $product
      * @param \Magento\Reports\Model\Event\TypeFactory $eventTypeFactory
      * @param \Magento\Catalog\Model\Product\Type $productType
-     * @param \Magento\CatalogInventory\Helper\Data $catalogInventoryData
+     * @param \Magento\CatalogInventory\Service\V1\StockItem $stockItemService
      * @param \Magento\CatalogInventory\Model\Resource\Stock\Item $itemResource
      * @param mixed $connection
-     * 
+     *
      * @SuppressWarnings(PHPMD.ExcessiveParameterList)
      */
     public function __construct(
@@ -108,7 +106,7 @@ class Collection extends \Magento\Reports\Model\Resource\Product\Collection
         \Magento\Catalog\Model\Resource\Product $product,
         \Magento\Reports\Model\Event\TypeFactory $eventTypeFactory,
         \Magento\Catalog\Model\Product\Type $productType,
-        \Magento\CatalogInventory\Helper\Data $catalogInventoryData,
+        \Magento\CatalogInventory\Service\V1\StockItem $stockItemService,
         \Magento\CatalogInventory\Model\Resource\Stock\Item $itemResource,
         $connection = null
     ) {
@@ -136,7 +134,7 @@ class Collection extends \Magento\Reports\Model\Resource\Product\Collection
             $productType,
             $connection
         );
-        $this->_inventoryData = $catalogInventoryData;
+        $this->stockItemService = $stockItemService;
         $this->_itemResource = $itemResource;
     }
 
@@ -265,7 +263,7 @@ class Collection extends \Magento\Reports\Model\Resource\Product\Collection
      */
     public function filterByIsQtyProductTypes()
     {
-        $this->filterByProductType(array_keys(array_filter($this->_inventoryData->getIsQtyTypeIds())));
+        $this->filterByProductType(array_keys(array_filter($this->stockItemService->getIsQtyTypeIds())));
         return $this;
     }
 
diff --git a/app/code/Magento/Sales/Block/Adminhtml/Order/Create/Items/Grid.php b/app/code/Magento/Sales/Block/Adminhtml/Order/Create/Items/Grid.php
index c58adca1e88..e814cc6f8ab 100644
--- a/app/code/Magento/Sales/Block/Adminhtml/Order/Create/Items/Grid.php
+++ b/app/code/Magento/Sales/Block/Adminhtml/Order/Create/Items/Grid.php
@@ -213,7 +213,6 @@ class Grid extends \Magento\Sales\Block\Adminhtml\Order\Create\AbstractCreate
      */
     public function getItemOrigPrice($item)
     {
-        //        return $this->convertPrice($item->getProduct()->getPrice());
         return $this->convertPrice($item->getPrice());
     }
 
diff --git a/app/code/Magento/Sales/sql/sales_setup/install-1.6.0.0.php b/app/code/Magento/Sales/sql/sales_setup/install-1.6.0.0.php
index 4a38a369081..b538fb3848b 100644
--- a/app/code/Magento/Sales/sql/sales_setup/install-1.6.0.0.php
+++ b/app/code/Magento/Sales/sql/sales_setup/install-1.6.0.0.php
@@ -5867,9 +5867,6 @@ $table = $installer->getConnection()->newTable(
     ),
     array('order_id', 'payment_id', 'txn_id'),
     array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-)->addIndex(
-    $installer->getIdxName('sales_payment_transaction', array('order_id')),
-    array('order_id')
 )->addIndex(
     $installer->getIdxName('sales_payment_transaction', array('parent_id')),
     array('parent_id')
diff --git a/app/code/Magento/SalesRule/sql/salesrule_setup/install-1.6.0.0.php b/app/code/Magento/SalesRule/sql/salesrule_setup/install-1.6.0.0.php
index 7efc97dbbbb..4889500270c 100644
--- a/app/code/Magento/SalesRule/sql/salesrule_setup/install-1.6.0.0.php
+++ b/app/code/Magento/SalesRule/sql/salesrule_setup/install-1.6.0.0.php
@@ -280,9 +280,6 @@ $table = $installer->getConnection()->newTable(
     null,
     array('unsigned' => true, 'nullable' => false, 'default' => '0'),
     'Times Used'
-)->addIndex(
-    $installer->getIdxName('salesrule_coupon_usage', array('coupon_id')),
-    array('coupon_id')
 )->addIndex(
     $installer->getIdxName('salesrule_coupon_usage', array('customer_id')),
     array('customer_id')
@@ -399,9 +396,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('salesrule_label', array('store_id')),
     array('store_id')
-)->addIndex(
-    $installer->getIdxName('salesrule_label', array('rule_id')),
-    array('rule_id')
 )->addForeignKey(
     $installer->getFkName('salesrule_label', 'rule_id', 'salesrule', 'rule_id'),
     'rule_id',
diff --git a/app/code/Magento/SalesRule/sql/salesrule_setup/upgrade-1.6.0.2-1.6.0.3.php b/app/code/Magento/SalesRule/sql/salesrule_setup/upgrade-1.6.0.2-1.6.0.3.php
index 05f7fa87ce9..f74e0dce97e 100644
--- a/app/code/Magento/SalesRule/sql/salesrule_setup/upgrade-1.6.0.2-1.6.0.3.php
+++ b/app/code/Magento/SalesRule/sql/salesrule_setup/upgrade-1.6.0.2-1.6.0.3.php
@@ -51,9 +51,6 @@ $table = $connection->newTable(
     null,
     array('unsigned' => true, 'nullable' => false, 'primary' => true),
     'Website Id'
-)->addIndex(
-    $installer->getIdxName('salesrule_website', array('rule_id')),
-    array('rule_id')
 )->addIndex(
     $installer->getIdxName('salesrule_website', array('website_id')),
     array('website_id')
@@ -96,9 +93,6 @@ $table = $connection->newTable(
     null,
     array('unsigned' => true, 'nullable' => false, 'primary' => true),
     'Customer Group Id'
-)->addIndex(
-    $installer->getIdxName('salesrule_customer_group', array('rule_id')),
-    array('rule_id')
 )->addIndex(
     $installer->getIdxName('salesrule_customer_group', array('customer_group_id')),
     array('customer_group_id')
diff --git a/app/code/Magento/Tax/sql/tax_setup/install-1.6.0.0.php b/app/code/Magento/Tax/sql/tax_setup/install-1.6.0.0.php
index c7ea81fba3d..dd256acaf23 100644
--- a/app/code/Magento/Tax/sql/tax_setup/install-1.6.0.0.php
+++ b/app/code/Magento/Tax/sql/tax_setup/install-1.6.0.0.php
@@ -83,8 +83,8 @@ $table = $installer->getConnection()->newTable(
     array('nullable' => false),
     'Position'
 )->addIndex(
-    $installer->getIdxName('tax_calculation_rule', array('priority', 'position', 'tax_calculation_rule_id')),
-    array('priority', 'position', 'tax_calculation_rule_id')
+    $installer->getIdxName('tax_calculation_rule', array('priority', 'position')),
+    array('priority', 'position')
 )->addIndex(
     $installer->getIdxName('tax_calculation_rule', array('code')),
     array('code')
@@ -207,9 +207,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('tax_calculation', array('tax_calculation_rule_id')),
     array('tax_calculation_rule_id')
-)->addIndex(
-    $installer->getIdxName('tax_calculation', array('tax_calculation_rate_id')),
-    array('tax_calculation_rate_id')
 )->addIndex(
     $installer->getIdxName('tax_calculation', array('customer_tax_class_id')),
     array('customer_tax_class_id')
@@ -297,9 +294,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('tax_calculation_rate_title', array('tax_calculation_rate_id', 'store_id')),
     array('tax_calculation_rate_id', 'store_id')
-)->addIndex(
-    $installer->getIdxName('tax_calculation_rate_title', array('tax_calculation_rate_id')),
-    array('tax_calculation_rate_id')
 )->addIndex(
     $installer->getIdxName('tax_calculation_rate_title', array('store_id')),
     array('store_id')
diff --git a/app/code/Magento/Tax/sql/tax_setup/upgrade-1.6.0.1-1.6.0.2.php b/app/code/Magento/Tax/sql/tax_setup/upgrade-1.6.0.1-1.6.0.2.php
index c180b398b5c..05307b452d9 100644
--- a/app/code/Magento/Tax/sql/tax_setup/upgrade-1.6.0.1-1.6.0.2.php
+++ b/app/code/Magento/Tax/sql/tax_setup/upgrade-1.6.0.1-1.6.0.2.php
@@ -48,9 +48,6 @@ $table = $installer->getConnection()->newTable(
     null,
     array('unsigned' => true, 'nullable' => false),
     'Item Id'
-)->addIndex(
-    $installer->getIdxName('sales_order_tax_item', array('tax_id')),
-    array('tax_id')
 )->addIndex(
     $installer->getIdxName('sales_order_tax_item', array('item_id')),
     array('item_id')
diff --git a/app/code/Magento/Theme/view/frontend/layout/page_calendar.xml b/app/code/Magento/Theme/view/frontend/layout/page_calendar.xml
index a0c8e1b6973..fc36123ffcc 100644
--- a/app/code/Magento/Theme/view/frontend/layout/page_calendar.xml
+++ b/app/code/Magento/Theme/view/frontend/layout/page_calendar.xml
@@ -27,7 +27,7 @@
     <referenceBlock name="head">
         <block class="Magento\Theme\Block\Html\Head\Script" name="jquery-jquery-ui-timepicker-addon-js">
             <arguments>
-                <argument name="file" xsi:type="string">jquery/jquery-ui-timepicker-addon-1.0.1.js</argument>
+                <argument name="file" xsi:type="string">jquery/jquery-ui-timepicker-addon.js</argument>
             </arguments>
         </block>
         <block class="Magento\Theme\Block\Html\Head\Script" name="magento-calendar-js">
diff --git a/app/code/Magento/Translation/sql/translation_setup/install-1.0.0.0.php b/app/code/Magento/Translation/sql/translation_setup/install-1.0.0.0.php
index 451def825c6..a5ddb80796b 100644
--- a/app/code/Magento/Translation/sql/translation_setup/install-1.0.0.0.php
+++ b/app/code/Magento/Translation/sql/translation_setup/install-1.0.0.0.php
@@ -94,9 +94,6 @@ $table = $installer->getConnection()
         ),
         array('store_id', 'locale', 'crc_string', 'string'),
         array('type' => \Magento\Framework\DB\Adapter\AdapterInterface::INDEX_TYPE_UNIQUE)
-    )->addIndex(
-        $installer->getIdxName('translation', array('store_id')),
-        array('store_id')
     )->addForeignKey(
         $installer->getFkName('translation', 'store_id', 'store', 'store_id'),
         'store_id',
diff --git a/app/code/Magento/UrlRewrite/sql/urlrewrite_setup/install-1.0.0.0.php b/app/code/Magento/UrlRewrite/sql/urlrewrite_setup/install-1.0.0.0.php
index 04d9e16e963..a443f9e819c 100644
--- a/app/code/Magento/UrlRewrite/sql/urlrewrite_setup/install-1.0.0.0.php
+++ b/app/code/Magento/UrlRewrite/sql/urlrewrite_setup/install-1.0.0.0.php
@@ -99,9 +99,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('core_url_rewrite', array('target_path', 'store_id')),
     array('target_path', 'store_id')
-)->addIndex(
-    $installer->getIdxName('core_url_rewrite', array('id_path')),
-    array('id_path')
 )->addIndex(
     $installer->getIdxName('core_url_rewrite', array('store_id')),
     array('store_id')
diff --git a/app/code/Magento/Webapi/Controller/Rest/Router.php b/app/code/Magento/Webapi/Controller/Rest/Router.php
index 11c846feb6c..639b5a08d79 100644
--- a/app/code/Magento/Webapi/Controller/Rest/Router.php
+++ b/app/code/Magento/Webapi/Controller/Rest/Router.php
@@ -55,13 +55,17 @@ class Router
     {
         /** @var \Magento\Webapi\Controller\Rest\Router\Route[] $routes */
         $routes = $this->_apiConfig->getRestRoutes($request);
+        $matched = [];
         foreach ($routes as $route) {
             $params = $route->match($request);
             if ($params !== false) {
                 $request->setParams($params);
-                return $route;
+                $matched[] = $route;
             }
         }
+        if (!empty($matched)) {
+            return array_pop($matched);
+        }
         throw new \Magento\Webapi\Exception(
             __('Request does not match any route.'),
             0,
diff --git a/app/code/Magento/Webapi/Controller/ServiceArgsSerializer.php b/app/code/Magento/Webapi/Controller/ServiceArgsSerializer.php
index f89ad856e69..f1fb175ebe7 100644
--- a/app/code/Magento/Webapi/Controller/ServiceArgsSerializer.php
+++ b/app/code/Magento/Webapi/Controller/ServiceArgsSerializer.php
@@ -92,7 +92,7 @@ class ServiceArgsSerializer
                 }
                 $inputData[] = $this->_convertValue($paramValue, $paramType);
             } else {
-                $inputData[] = $param->getDefaultValue(); // not set, so use default
+                $inputData[] = $param->isDefaultValueAvailable() ? $param->getDefaultValue() : null;
             }
         }
 
diff --git a/app/code/Magento/Webapi/Model/Rest/Config.php b/app/code/Magento/Webapi/Model/Rest/Config.php
index 33f4f298eef..5111a6b6a82 100644
--- a/app/code/Magento/Webapi/Model/Rest/Config.php
+++ b/app/code/Magento/Webapi/Model/Rest/Config.php
@@ -156,7 +156,9 @@ class Config
         $serviceBaseUrl = $this->_getServiceBaseUrl($request);
         $requestHttpMethod = $request->getHttpMethod();
         $routes = array();
-        foreach ($this->_config->getServices()[Converter::KEY_ROUTES] as $url => $httpMethods) {
+        $servicesRoutes = $this->_config->getServices()[Converter::KEY_ROUTES];
+        ksort($servicesRoutes, SORT_STRING);
+        foreach ($servicesRoutes as $url => $httpMethods) {
             // skip if baseurl is not null and does not match
             if (!$serviceBaseUrl || strpos(trim($url, '/'), trim($serviceBaseUrl, '/')) !== 0) {
                 // base url does not match, just skip this service
diff --git a/app/code/Magento/Widget/sql/widget_setup/install-1.6.0.0.php b/app/code/Magento/Widget/sql/widget_setup/install-1.6.0.0.php
index dc629c32d3e..189db7d90bc 100644
--- a/app/code/Magento/Widget/sql/widget_setup/install-1.6.0.0.php
+++ b/app/code/Magento/Widget/sql/widget_setup/install-1.6.0.0.php
@@ -258,9 +258,6 @@ $table = $installer->getConnection()->newTable(
 )->addIndex(
     $installer->getIdxName('widget_instance_page_layout', 'page_id'),
     'page_id'
-)->addIndex(
-    $installer->getIdxName('widget_instance_page_layout', 'layout_update_id'),
-    'layout_update_id'
 )->addIndex(
     $installer->getIdxName(
         'widget_instance_page_layout',
diff --git a/app/code/Magento/Wishlist/Model/Resource/Item/Collection.php b/app/code/Magento/Wishlist/Model/Resource/Item/Collection.php
index 554d66340db..64f2f263c29 100644
--- a/app/code/Magento/Wishlist/Model/Resource/Item/Collection.php
+++ b/app/code/Magento/Wishlist/Model/Resource/Item/Collection.php
@@ -21,15 +21,11 @@
  * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
-
+namespace Magento\Wishlist\Model\Resource\Item;
 
 /**
  * Wishlist item collection
- *
- * @author      Magento Core Team <core@magentocommerce.com>
  */
-namespace Magento\Wishlist\Model\Resource\Item;
-
 class Collection extends \Magento\Framework\Model\Resource\Db\Collection\AbstractCollection
 {
     /**
@@ -270,7 +266,10 @@ class Collection extends \Magento\Framework\Model\Resource\Db\Collection\Abstrac
      */
     protected function _assignProducts()
     {
-        \Magento\Framework\Profiler::start('WISHLIST:' . __METHOD__, array('group' => 'WISHLIST', 'method' => __METHOD__));
+        \Magento\Framework\Profiler::start(
+            'WISHLIST:' . __METHOD__,
+            array('group' => 'WISHLIST', 'method' => __METHOD__)
+        );
         $productIds = array();
 
         $this->_productIds = array_merge($this->_productIds, array_keys($productIds));
@@ -282,11 +281,12 @@ class Collection extends \Magento\Framework\Model\Resource\Db\Collection\Abstrac
             $productCollection->setVisibility($this->_productVisibility->getVisibleInSiteIds());
         }
 
-        $productCollection->addPriceData()->addTaxPercents()->addIdFilter(
-            $this->_productIds
-        )->addAttributeToSelect(
-            $attributes
-        )->addOptionsToResult()->addUrlRewrite();
+        $productCollection->addPriceData()
+            ->addTaxPercents()
+            ->addIdFilter($this->_productIds)
+            ->addAttributeToSelect($attributes)
+            ->addOptionsToResult()
+            ->addUrlRewrite();
 
         if ($this->_productSalable) {
             $productCollection = $this->_adminhtmlSales->applySalableProductTypesFilter($productCollection);
@@ -464,13 +464,19 @@ class Collection extends \Magento\Framework\Model\Resource\Db\Collection\Abstrac
         $now = $this->_date->date();
         $gmtOffset = (int)$this->_date->getGmtOffset();
         if (isset($constraints['from'])) {
-            $lastDay = new \Magento\Framework\Stdlib\DateTime\Date($now, \Magento\Framework\Stdlib\DateTime::DATETIME_INTERNAL_FORMAT);
+            $lastDay = new \Magento\Framework\Stdlib\DateTime\Date(
+                $now,
+                \Magento\Framework\Stdlib\DateTime::DATETIME_INTERNAL_FORMAT
+            );
             $lastDay->subSecond($gmtOffset)->subDay(intval($constraints['from']));
             $filter['to'] = $lastDay;
         }
 
         if (isset($constraints['to'])) {
-            $firstDay = new \Magento\Framework\Stdlib\DateTime\Date($now, \Magento\Framework\Stdlib\DateTime::DATETIME_INTERNAL_FORMAT);
+            $firstDay = new \Magento\Framework\Stdlib\DateTime\Date(
+                $now,
+                \Magento\Framework\Stdlib\DateTime::DATETIME_INTERNAL_FORMAT
+            );
             $firstDay->subSecond($gmtOffset)->subDay(intval($constraints['to']) + 1);
             $filter['from'] = $firstDay;
         }
diff --git a/app/design/adminhtml/Magento/backend/web/css/admin.less b/app/design/adminhtml/Magento/backend/web/css/admin.less
index 3a9e4d2cc35..bd89088c42b 100644
--- a/app/design/adminhtml/Magento/backend/web/css/admin.less
+++ b/app/design/adminhtml/Magento/backend/web/css/admin.less
@@ -831,8 +831,8 @@ input.mage-error ~ .addafter {
 .fieldset {
     background: #fff;
     border: 0;
-    margin: 0 0 20px;
-    padding: 5px 18px 18px;
+    margin: 0;
+    padding: 5px 18px 38px;
     position: relative;
 }
 
@@ -1012,7 +1012,9 @@ input.mage-error ~ .addafter {
     margin: 0 0 29px;
 }
 
-.with-note .note, .field .note {
+.with-note .note,
+.field .note,
+.data-table .note {
     .style19();
 }
 
diff --git a/app/design/adminhtml/Magento/backend/web/css/source/table.less b/app/design/adminhtml/Magento/backend/web/css/source/table.less
index 78bb5dd66fd..2b95c3b3630 100644
--- a/app/design/adminhtml/Magento/backend/web/css/source/table.less
+++ b/app/design/adminhtml/Magento/backend/web/css/source/table.less
@@ -644,7 +644,8 @@ td.col-sku {
 
     .col-file {
         white-space: nowrap;
-        input {
+        input,
+        .input-text {
             margin: 0 5px;
             width: 40%;
             &:first-child {
diff --git a/app/design/adminhtml/Magento/backend/web/mui/form.css b/app/design/adminhtml/Magento/backend/web/mui/form.css
index 4acdd9d45f7..8f769cf1e2f 100644
--- a/app/design/adminhtml/Magento/backend/web/mui/form.css
+++ b/app/design/adminhtml/Magento/backend/web/mui/form.css
@@ -237,7 +237,8 @@ span.required {
 }
 
 .with-note .note,
-.field .note {
+.field .note,
+.data-table .note {
     font-size: 11px;
     padding-left: 15px;
     margin: 5px 0;
@@ -245,7 +246,8 @@ span.required {
 }
 
 .with-note .note:before,
-.field .note:before {
+.field .note:before,
+.data-table .note:before {
     position: absolute;
     margin: 4px 0 0 -14px;
     content: '';
diff --git a/dev/shell/install.php b/dev/shell/install.php
index 07e1e281a43..cb8406e18e2 100644
--- a/dev/shell/install.php
+++ b/dev/shell/install.php
@@ -92,5 +92,9 @@ INSTALLSCHEME;
 define('BARE_BOOTSTRAP', 1);
 require_once __DIR__ . '/../../app/bootstrap.php';
 
+$_SERVER[\Magento\Framework\App\State::PARAM_MODE] = isset($_SERVER[\Magento\Framework\App\State::PARAM_MODE])
+    ? $_SERVER[\Magento\Framework\App\State::PARAM_MODE]
+    : \Magento\Framework\App\State::MODE_DEVELOPER;
+
 $entryPoint = new \Magento\Framework\App\EntryPoint\EntryPoint(BP, $_SERVER);
 $entryPoint->run('Magento\Install\App\Console', array('arguments' => $args));
diff --git a/dev/tests/functional/etc/global/events.xml b/dev/tests/functional/etc/global/events.xml
new file mode 100644
index 00000000000..34b2f90134d
--- /dev/null
+++ b/dev/tests/functional/etc/global/events.xml
@@ -0,0 +1,27 @@
+<?xml version="1.0"?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="events.xsd">
+</config>
diff --git a/dev/tests/functional/etc/global/events.xsd b/dev/tests/functional/etc/global/events.xsd
new file mode 100644
index 00000000000..61361a7b0db
--- /dev/null
+++ b/dev/tests/functional/etc/global/events.xsd
@@ -0,0 +1,96 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+/**
+ * This schema must be used to validate events.xml files
+ *
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
+    <xs:element name="config">
+        <xs:complexType>
+            <xs:sequence minOccurs="0" maxOccurs="unbounded">
+                <xs:element type="preset" name="preset">
+                    <xs:unique name="uniqueObserverClass">
+                        <xs:annotation>
+                            <xs:documentation>
+                                Observer class must be unique.
+                            </xs:documentation>
+                        </xs:annotation>
+                        <xs:selector xpath="observer"/>
+                        <xs:field xpath="@class"/>
+                    </xs:unique>
+                </xs:element>
+            </xs:sequence>
+        </xs:complexType>
+        <xs:unique name="uniquePresetName">
+            <xs:annotation>
+                <xs:documentation>
+                    Preset name must be unique.
+                </xs:documentation>
+            </xs:annotation>
+            <xs:selector xpath="preset"/>
+            <xs:field xpath="@name"/>
+        </xs:unique>
+    </xs:element>
+
+    <xs:complexType name="preset">
+        <xs:sequence minOccurs="0" maxOccurs="unbounded">
+            <xs:element type="observer" name="observer">
+                <xs:unique name="uniqueTagName">
+                    <xs:annotation>
+                        <xs:documentation>
+                            Tag name must be unique.
+                        </xs:documentation>
+                    </xs:annotation>
+                    <xs:selector xpath="tag"/>
+                    <xs:field xpath="@name"/>
+                </xs:unique>
+            </xs:element>
+        </xs:sequence>
+        <xs:attribute type="xs:string" name="name" use="required"/>
+        <xs:attribute type="xs:string" name="extends" use="optional"/>
+    </xs:complexType>
+
+
+    <xs:complexType name="observer">
+        <xs:annotation>
+            <xs:documentation>
+                Observer node with all attached tags for events inside
+            </xs:documentation>
+        </xs:annotation>
+        <xs:sequence minOccurs="0" maxOccurs="unbounded">
+            <xs:element type="tag" name="tag" minOccurs="0" maxOccurs="unbounded"/>
+        </xs:sequence>
+        <xs:attribute type="xs:string" name="class" use="required"/>
+    </xs:complexType>
+
+    <xs:complexType name="tag">
+        <xs:annotation>
+            <xs:documentation>
+                Tag with name to look for
+            </xs:documentation>
+        </xs:annotation>
+        <xs:attribute type="xs:string" name="name" use="required"/>
+    </xs:complexType>
+
+</xs:schema>
\ No newline at end of file
diff --git a/dev/tests/functional/lib/Mtf/Client/Driver/Selenium/Element/ConditionsElement.php b/dev/tests/functional/lib/Mtf/Client/Driver/Selenium/Element/ConditionsElement.php
new file mode 100644
index 00000000000..e8d5572c935
--- /dev/null
+++ b/dev/tests/functional/lib/Mtf/Client/Driver/Selenium/Element/ConditionsElement.php
@@ -0,0 +1,393 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Mtf\Client\Driver\Selenium\Element;
+
+use Mtf\Client\Element;
+use Mtf\Client\Element\Locator;
+use Mtf\Client\Driver\Selenium\Element as AbstractElement;
+
+/**
+ * Class ConditionsElement
+ * Typified element class for conditions
+ *
+ * Format value.
+ * Add slash to symbols: "{", "}", "[", "]", ":".
+ * 1. Single condition:
+ * [Type|Param|Param|...|Param]
+ * 2. List conditions:
+ * [Type|Param|Param|...|Param]
+ * [Type|Param|Param|...|Param]
+ * [Type|Param|Param|...|Param]
+ * 3. Combination condition with single condition
+ * {Type|Param|Param|...|Param:[Type|Param|Param|...|Param]}
+ * 4. Combination condition with list conditions
+ * {Type|Param|Param|...|Param:[[Type|Param|...|Param][Type|Param|...|Param]...[Type|Param|...|Param]]}
+ *
+ * Example value:
+ * {Products subselection|total amount|greater than|135|ANY:[[Price in cart|is|100][Quantity in cart|is|100]]}
+ * {Conditions combination:[
+ *     [Subtotal|is|100]
+ *     {Product attribute combination|NOT FOUND|ANY:[[Attribute Set|is|Default][Attribute Set|is|Default]]}
+ * ]}
+ */
+class ConditionsElement extends AbstractElement
+{
+    /**
+     * Main condition
+     *
+     * @var string
+     */
+    protected $mainCondition = './/ul[contains(@id,"__1__children")]/..';
+
+    /**
+     * Button add condition
+     *
+     * @var string
+     */
+    protected $addNew = './/*[contains(@class,"rule-param-new-child")]/a';
+
+    /**
+     * Button remove condition
+     *
+     * @var string
+     */
+    protected $remove = './/*/a[@class="rule-param-remove"]';
+
+    /**
+     * New condition
+     *
+     * @var string
+     */
+    protected $newCondition = './ul/li/span[contains(@class,"rule-param-new-child")]/..';
+
+    /**
+     * Type of new condition
+     *
+     * @var string
+     */
+    protected $typeNew = './/*[@class="element"]/select';
+
+    /**
+     * Created condition
+     *
+     * @var string
+     */
+    protected $created = './/preceding-sibling::li[1]';
+
+    /**
+     * Children condition
+     *
+     * @var string
+     */
+    protected $children = './/ul[contains(@id,"conditions__")]';
+
+    /**
+     * Parameter of condition
+     *
+     * @var string
+     */
+    protected $param = './span[@class="rule-param"]/span/*[substring(@id,(string-length(@id)-%d+1))="%s"]/../..';
+
+    /**
+     * Key of last find param
+     *
+     * @var int
+     */
+    protected $findKeyParam = 0;
+
+    /**
+     * Map of parameters
+     *
+     * @var array
+     */
+    protected $mapParams = [
+        'attribute',
+        'operator',
+        'value_type',
+        'value',
+        'aggregator',
+    ];
+
+    /**
+     * Map encode special chars
+     *
+     * @var array
+     */
+    protected $encodeChars = [
+        '\{' => '&lbrace;',
+        '\}' => '&rbrace;',
+        '\[' => '&lbracket;',
+        '\]' => '&rbracket;',
+        '\:' => '&colon;',
+    ];
+
+    /**
+     * Map decode special chars
+     *
+     * @var array
+     */
+    protected $decodeChars = [
+        '&lbrace;' => '{',
+        '&rbrace;' => '}',
+        '&lbracket;' => '[',
+        '&rbracket;' => ']',
+        '&colon;' => ':',
+    ];
+
+    /**
+     * Magento varienLoader.js loader
+     *
+     * @var string
+     */
+    protected $loader = './/ancestor::body/div[@id="loading-mask"]';
+
+    /**
+     * Set value to conditions
+     *
+     * @param string $value
+     * @return void
+     */
+    public function setValue($value)
+    {
+        $conditions = $this->decodeValue($value);
+        $context = $this->find($this->mainCondition, Locator::SELECTOR_XPATH);
+        $this->clear();
+        $this->addMultipleCondition($conditions, $context);
+    }
+
+    /**
+     * Add condition combination
+     *
+     * @param string $condition
+     * @param Element $context
+     * @return Element
+     */
+    protected function addConditionsCombination($condition, Element $context)
+    {
+        $condition = $this->parseCondition($condition);
+        $newCondition = $context->find($this->newCondition, Locator::SELECTOR_XPATH);
+        $newCondition->find($this->addNew, Locator::SELECTOR_XPATH)->click();
+        $typeNewCondition = $newCondition->find($this->typeNew, Locator::SELECTOR_XPATH, 'select');
+        $typeNewCondition->setValue($condition['type']);
+        $this->waitLoader();
+
+        $createdCondition = $newCondition->find($this->created, Locator::SELECTOR_XPATH);
+        if (!empty($condition['rules'])) {
+            $this->fillCondition($condition['rules'], $createdCondition);
+        }
+        return $createdCondition;
+    }
+
+    /**
+     * Add conditions
+     *
+     * @param array $conditions
+     * @param Element $context
+     * @return void
+     */
+    protected function addMultipleCondition(array $conditions, Element $context)
+    {
+        foreach ($conditions as $key => $condition) {
+            $elementContext = is_numeric($key) ? $context : $this->addConditionsCombination($key, $context);
+            if (is_string($condition)) {
+                $this->addSingleCondition($condition, $elementContext);
+            } else {
+                $this->addMultipleCondition($condition, $elementContext);
+            }
+        }
+    }
+
+    /**
+     * Add single Condition
+     *
+     * @param string $condition
+     * @param Element $context
+     * @return void
+     */
+    protected function addSingleCondition($condition, Element $context)
+    {
+        $condition = $this->parseCondition($condition);
+
+        $newCondition = $context->find($this->newCondition, Locator::SELECTOR_XPATH);
+        $newCondition->find($this->addNew, Locator::SELECTOR_XPATH)->click();
+        $newCondition->find($this->typeNew, Locator::SELECTOR_XPATH, 'select')->setValue($condition['type']);
+        $this->waitLoader();
+
+        $createdCondition = $newCondition->find($this->created, Locator::SELECTOR_XPATH);
+        $this->fillCondition($condition['rules'], $createdCondition);
+    }
+
+    /**
+     * Fill single condition
+     *
+     * @param array $rules
+     * @param Element $element
+     * @return void
+     * @throws \Exception
+     */
+    protected function fillCondition(array $rules, Element $element)
+    {
+        $this->resetKeyParam();
+        foreach ($rules as $rule) {
+            $param = $this->findNextParam($element);
+            $param->find('a')->click();
+
+            $value = $param->find('select', Locator::SELECTOR_CSS, 'select');
+            if ($value->isVisible()) {
+                $value->setValue($rule);
+                continue;
+            }
+            $value = $param->find('input');
+            if ($value->isVisible()) {
+                $value->setValue($rule);
+
+                $apply = $param->find('.//*[@class="rule-param-apply"]', Locator::SELECTOR_XPATH);
+                if ($apply->isVisible()) {
+                    $apply->click();
+                }
+                continue;
+            }
+            throw new \Exception('Undefined type of value ');
+        }
+    }
+
+    /**
+     * Decode value
+     *
+     * @param string $value
+     * @return array
+     * @throws \Exception
+     */
+    protected function decodeValue($value)
+    {
+        $value = str_replace(array_keys($this->encodeChars), $this->encodeChars, $value);
+        $value = preg_replace('/(\]|})({|\[)/', '$1,$2', $value);
+        $value = preg_replace('/{([^:]+):/', '{"$1":', $value);
+        $value = preg_replace('/\[([^\[{])/', '"$1', $value);
+        $value = preg_replace('/([^\]}])\]/', '$1"', $value);
+        $value = str_replace(array_keys($this->decodeChars), $this->decodeChars, $value);
+
+        $value = "[{$value}]";
+        $value = json_decode($value, true);
+        if (null === $value) {
+            throw new \Exception('Bad format value.');
+        }
+        return $value;
+    }
+
+    /**
+     * Parse condition
+     *
+     * @param string $condition
+     * @return array
+     * @throws \Exception
+     */
+    protected function parseCondition($condition)
+    {
+        if (!preg_match_all('/([^|]+\|?)/', $condition, $match)) {
+            throw new \Exception('Bad format condition');
+        }
+        foreach ($match[1] as $key => $value) {
+            $match[1][$key] = rtrim($value, '|');
+        }
+
+        return [
+            'type' => array_shift($match[1]),
+            'rules' => array_values($match[1]),
+        ];
+    }
+
+    /**
+     * Find next param of condition for fill
+     *
+     * @param Element $context
+     * @return Element
+     * @throws \Exception
+     */
+    protected function findNextParam(Element $context)
+    {
+        do {
+            if (!isset($this->mapParams[$this->findKeyParam])) {
+                throw new \Exception("Empty map of params");
+            }
+            $param = $this->mapParams[$this->findKeyParam];
+            $element = $context->find(sprintf($this->param, strlen($param), $param), Locator::SELECTOR_XPATH);
+            $this->findKeyParam += 1;
+        } while (!$element->isVisible());
+
+        return $element;
+    }
+
+    /**
+     * Reset key of last find param
+     *
+     * @return void
+     */
+    protected function resetKeyParam()
+    {
+        $this->findKeyParam = 0;
+    }
+
+    /**
+     * Wait loader
+     *
+     * @return void
+     */
+    protected function waitLoader()
+    {
+        $browser = $this;
+        $loader = $this->loader;
+        $browser->waitUntil(
+            function () use ($browser, $loader) {
+                $element = $browser->find($loader, Locator::SELECTOR_XPATH);
+                return $element->isVisible() ? null : true;
+            }
+        );
+    }
+
+    /**
+     * Clear conditions
+     *
+     * @return void
+     */
+    protected function clear()
+    {
+        $remote = $this->find($this->remove, Locator::SELECTOR_XPATH);
+        while ($remote->isVisible()) {
+            $remote->click();
+            $remote = $this->find($this->remove, Locator::SELECTOR_XPATH);
+        }
+    }
+
+    /**
+     * Get value from conditions
+     *
+     * @return null
+     */
+    public function getValue()
+    {
+        return null;
+    }
+}
diff --git a/dev/tests/functional/lib/Mtf/Client/Driver/Selenium/Element/MultiselectgrouplistElement.php b/dev/tests/functional/lib/Mtf/Client/Driver/Selenium/Element/MultiselectgrouplistElement.php
new file mode 100644
index 00000000000..f205f6e3d45
--- /dev/null
+++ b/dev/tests/functional/lib/Mtf/Client/Driver/Selenium/Element/MultiselectgrouplistElement.php
@@ -0,0 +1,312 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Mtf\Client\Driver\Selenium\Element;
+
+use Mtf\Client\Element;
+use Mtf\Client\Element\Locator;
+
+/**
+ * Class MultiselectgrouplistElement
+ * Typified element class for multiselect with group
+ */
+class MultiselectgrouplistElement extends MultiselectElement
+{
+    /**
+     * Indent length
+     */
+    const INDENT_LENGTH = 4;
+
+    /**
+     * Locator for search optgroup by label
+     *
+     * @var string
+     */
+    protected $optgroupByLabel = './/optgroup[@label="%s"]';
+
+    /**
+     * Locator for search optgroup by number
+     *
+     * @var string
+     */
+    protected $optgroupByNumber = './/optgroup[%d]';
+
+    /**
+     * Locator for search next optgroup
+     *
+     * @var string
+     */
+    protected $nextOptgroup = './/following-sibling::optgroup[%d]';
+
+    /**
+     * Locator for search child optgroup
+     *
+     * @var string
+     */
+    protected $childOptgroup = ".//following-sibling::optgroup[%d][@label='%s']";
+
+    /**
+     * Locator for search parent optgroup
+     *
+     * @var string
+     */
+    protected $parentOptgroup = 'optgroup[option[text()="%s"]]';
+
+    /**
+     * Locator for search preceding sibling optgroup
+     *
+     * @var string
+     */
+    protected $precedingOptgroup = '/preceding-sibling::optgroup[1][substring(@label,1,%d)="%s"]';
+
+    /**
+     * Locator for option
+     *
+     * @var string
+     */
+    protected $option = './/option[text()="%s"]';
+
+    /**
+     * Locator search for option by number
+     *
+     * @var string
+     */
+    protected $optionByNumber = './/optgroup[%d]/option[%d]';
+
+    /**
+     * Indent, four symbols non breaking space
+     *
+     * @var string
+     */
+    protected $indent = "\xC2\xA0\xC2\xA0\xC2\xA0\xC2\xA0";
+
+    /**
+     * Trim symbols
+     *
+     * @var string
+     */
+    protected $trim = "\xC2\xA0 ";
+
+    /**
+     * Set values
+     *
+     * @param array|string $values
+     * @return void
+     */
+    public function setValue($values)
+    {
+        $this->clearSelectedOptions();
+        $values = is_array($values) ? $values : [$values];
+        foreach ($values as $value) {
+            $this->selectOption($value);
+        }
+    }
+
+    /**
+     * Select option
+     *
+     * @param string $option
+     * @return void
+     * @throws \Exception
+     */
+    protected function selectOption($option)
+    {
+        $isOptgroup = false;
+        $optgroupIndent = '';
+        $values = explode('/', $option);
+        $context = $this;
+
+        foreach ($values as $value) {
+            $optionIndent = $isOptgroup ? $this->indent : '';
+            $optionElement = $context->find(sprintf($this->option, $optionIndent . $value), Locator::SELECTOR_XPATH);
+            if ($optionElement->isVisible()) {
+                if (!$optionElement->isSelected()) {
+                    $optionElement->click();
+                }
+                return;
+            }
+
+            $value = $optgroupIndent . $value;
+            $optgroupIndent .= $this->indent;
+            if ($isOptgroup) {
+                $context = $this->getChildOptgroup($value, $context);
+            } else {
+                $context = $this->getOptgroup($value, $context);
+                $isOptgroup = true;
+            }
+        }
+        throw new \Exception("Can't find option \"{$option}\".");
+    }
+
+    /**
+     * Get optgroup
+     *
+     * @param string $value
+     * @param Element $context
+     * @return Element
+     * @throws \Exception
+     */
+    protected function getOptgroup($value, Element $context)
+    {
+        $optgroup = $context->find(sprintf($this->optgroupByLabel, $value), Locator::SELECTOR_XPATH);
+        if (!$optgroup->isVisible()) {
+            throw new \Exception("Can't find group \"{$value}\".");
+        }
+        return $optgroup;
+    }
+
+    /**
+     * Get child optgroup
+     *
+     * @param string $value
+     * @param Element $context
+     * @return Element
+     * @throws \Exception
+     */
+    protected function getChildOptgroup($value, Element $context)
+    {
+        $childOptgroup = null;
+        $count = 1;
+        while (!$childOptgroup) {
+            $optgroup = $context->find(sprintf($this->nextOptgroup, $count), Locator::SELECTOR_XPATH);
+            if (!$optgroup->isVisible()) {
+                throw new \Exception("Can't find child group \"{$value}\"");
+            }
+
+            $childOptgroup = $context->find(
+                sprintf($this->childOptgroup, $count, $value),
+                Locator::SELECTOR_XPATH
+            );
+            if (!$childOptgroup->isVisible()) {
+                $childOptgroup = null;
+            }
+            ++$count;
+        }
+
+        return $childOptgroup;
+    }
+
+    /**
+     * Get value
+     *
+     * @return array
+     */
+    public function getValue()
+    {
+        $values = [];
+        $indentOption = str_repeat(' ', self::INDENT_LENGTH);
+
+        foreach ($this->getSelectedOptions() as $option) {
+            $value = [];
+
+            /** @var Element $option */
+            $optionText = $option->getText();
+            $optionValue = trim($optionText, $this->trim);
+            $value[] = $optionValue;
+            if (0 !== strpos($optionText, $indentOption)) {
+                $values[] = implode('/', $value);
+                continue;
+            }
+
+            $pathOptgroup = sprintf($this->parentOptgroup, $this->indent . $optionValue);
+            $optgroup = $this->_getWrappedElement()->byXPath($pathOptgroup);
+            $optgroupText = $optgroup->attribute('label');
+            $optgroupValue = trim($optgroupText, $this->trim);
+            $amountIndent = strlen($optgroupText) - strlen($optgroupValue);
+            $amountIndent = $amountIndent ? ($amountIndent / strlen($this->indent)) : 0;
+            $value[] = $optgroupValue;
+            if (0 == $amountIndent) {
+                $values[] = implode('/', $value);
+                continue;
+            }
+
+            --$amountIndent;
+            $indent = $amountIndent ? str_repeat($this->indent, $amountIndent) : '';
+            $pathOptgroup .= sprintf($this->precedingOptgroup, $amountIndent * self::INDENT_LENGTH, $indent);
+            while (0 <= $amountIndent && $this->find($pathOptgroup, Locator::SELECTOR_XPATH)->isVisible()) {
+                $optgroup = $this->_getWrappedElement()->byXPath($pathOptgroup);
+                $optgroupText = $optgroup->attribute('label');
+                $optgroupValue = trim($optgroupText, $this->trim);
+                $value[] = $optgroupValue;
+
+                --$amountIndent;
+                $indent = (0 < $amountIndent) ? str_repeat($this->indent, $amountIndent) : '';
+                $pathOptgroup .= sprintf($this->precedingOptgroup, $amountIndent * self::INDENT_LENGTH, $indent);
+            }
+
+            $values[] = implode('/', array_reverse($value));
+        }
+
+        return $values;
+    }
+
+    /**
+     * Get options
+     *
+     * @return array
+     */
+    protected function getOptions()
+    {
+        $options = [];
+
+        $countOptgroup = 1;
+        $optgroup = $this->find(sprintf($this->optgroupByNumber, $countOptgroup), Locator::SELECTOR_XPATH);
+        while ($optgroup->isVisible()) {
+            $countOption = 1;
+            $option = $this->find(
+                sprintf($this->optionByNumber, $countOptgroup, $countOption),
+                Locator::SELECTOR_XPATH
+            );
+            while ($option->isVisible()) {
+                $options[] = $option;
+                ++$countOption;
+                $option = $this->find(
+                    sprintf($this->optionByNumber, $countOptgroup, $countOption),
+                    Locator::SELECTOR_XPATH
+                );
+            }
+
+            ++$countOptgroup;
+            $optgroup = $this->find(sprintf($this->optgroupByNumber, $countOptgroup), Locator::SELECTOR_XPATH);
+        }
+        return $options;
+    }
+
+    /**
+     * Get selected options
+     *
+     * @return array
+     */
+    protected function getSelectedOptions()
+    {
+        $options = [];
+        foreach ($this->getOptions() as $option) {
+            /** Element $option */
+            if ($option->isSelected()) {
+                $options[] = $option;
+            }
+        }
+        return $options;
+    }
+}
diff --git a/dev/tests/functional/lib/Mtf/Util/Generate/Fixture/FieldsProvider.php b/dev/tests/functional/lib/Mtf/Util/Generate/Fixture/FieldsProvider.php
index 6b695370821..47708c40bf3 100644
--- a/dev/tests/functional/lib/Mtf/Util/Generate/Fixture/FieldsProvider.php
+++ b/dev/tests/functional/lib/Mtf/Util/Generate/Fixture/FieldsProvider.php
@@ -139,4 +139,35 @@ class FieldsProvider implements FieldsProviderInterface
 
         return $attributes;
     }
+
+    /**
+     * Collect fields for the entity with composite type
+     *
+     * @param array $fixture
+     * @return array
+     */
+    protected function compositeCollectFields(array $fixture)
+    {
+        $entityTypes = $fixture['entities'];
+
+        /** @var $connection \Magento\Framework\DB\Adapter\AdapterInterface */
+        $connection = $this->resource->getConnection('core_write');
+        $fields = [];
+        foreach ($entityTypes as $entityType) {
+            $fields = array_merge($fields, $connection->describeTable($entityType));
+        }
+
+        $attributes = [];
+        foreach ($fields as $code => $field) {
+            $attributes[$code] = [
+                'attribute_code' => $code,
+                'backend_type' => $field['DATA_TYPE'],
+                'is_required' => ($field['PRIMARY'] || $field['IDENTITY']),
+                'default_value' => $field['DEFAULT'],
+                'input' => ''
+            ];
+        }
+
+        return $attributes;
+    }
 }
diff --git a/dev/tests/functional/lib/Mtf/Util/Generate/testcase.xml b/dev/tests/functional/lib/Mtf/Util/Generate/testcase.xml
index 79bbd38c3df..8ba82ffa968 100644
--- a/dev/tests/functional/lib/Mtf/Util/Generate/testcase.xml
+++ b/dev/tests/functional/lib/Mtf/Util/Generate/testcase.xml
@@ -25,115 +25,23 @@
 -->
 <testcases>
   <testcase module="Magento\Tax">
-    <id>MTA-3</id>
-    <inject>
-      <page>
-        <class>\Magento\Tax\Test\Page\TaxRule</class>
-      </page>
-    </inject>
-    <invoke>
-      <tax_rule>
-        <class>\Magento\Tax\Test\Fixture\TaxRule</class>
-      </tax_rule>
-    </invoke>
-    <name>CreateTaxRuleEntityTest</name>
-    <description>Test Creation for Create TaxRuleEntity with fucntional test designed for automation</description>
-    <module>Sales</module>
+    <id>MTA-120</id>
+    <ticketId>MTA-120</ticketId>
+    <name>CreateTaxRateEntityTest</name>
+    <description>Test Creation for CreateTaxRateEntity</description>
+    <module>Tax</module>
     <components>
       <component>Tax (CS)</component>
     </components>
-    <testId>MAGETWO-20913</testId>
-    <ticketId>MTA-3</ticketId>
-    <steps/>
-  </testcase>
-  <testcase module="Magento\Catalog">
-    <id>MTA-179</id>
-    <ticketId>MTA-179</ticketId>
-    <name>CreateSimpleProductEntityTest</name>
-    <description>Test Creation for CreateSimpleProductEntity</description>
-    <module>Catalog</module>
-    <components>
-      <component>Products (CS)</component>
-    </components>
     <steps>
-      <step>Login to the backend.</step>
-      <step>Navigate to Products &gt; Catalog.</step>
-      <step>Start to create simple product.</step>
-      <step>Fill in data according to attached data set.</step>
-      <step>Save Product.</step>
-      <step>Perform appropriate assertions.</step>
-    </steps>
-  </testcase>
-  <testcase>
-    <id>MTA-42</id>
-    <ticketId>MTA-42</ticketId>
-    <name>CreateCustomerGroupEntityTest</name>
-    <description>Test Creation for CreateCustomerGroupEntity</description>
-    <module>Customer</module>
-    <components>
-      <component>Customer Groups (MX)</component>
-    </components>
-    <steps>
-      <step>Log in to backend as admin user.</step>
-      <step>Navigate to Stores&gt;Other Settings&gt;Customer Groups.</step>
-      <step>Start to create new Customer Group.</step>
-      <step>Fill in all data according to data set.</step>
-      <step>Click "Save Customer Group" button.</step>
-      <step>Perform all assertions.</step>
-    </steps>
-  </testcase>
-  <testcase>
-    <id>MTA-164</id>
-    <ticketId>MTA-164</ticketId>
-    <name>CreateNewsletterTemplateEntityTest</name>
-    <description>Test Creation for Create Newsletter Template Entity</description>
-    <module>Newsletter</module>
-    <components>
-      <component>Newsletters (MX)</component>
-    </components>
-    <steps>
-      <step>Login to backend.</step>
-      <step>Navigate to MARKETING -&gt; Newsletter Template.</step>
-      <step>Add New Template.</step>
-      <step>Fill in all data according to data set.</step>
-      <step>Save.</step>
-      <step>Perform asserts.</step>
-    </steps>
-  </testcase>
-  <testcase>
-    <id>MTA-25</id>
-    <ticketId>MTA-25</ticketId>
-    <name>UpdateProductSimpleEntityTest</name>
-    <description>Cover UpdateProductSimpleEntity with fucntional tests designed for automation</description>
-    <module>Catalog</module>
-    <components>
-      <component>Products (CS)</component>
-    </components>
-    <steps>
-      <step>Login to backend.</step>
-      <step>Navigate to PRODUCTS &gt; Catalog.</step>
-      <step>Select a product in the grid.</step>
-      <step>Edit test value(s) according to dataset.</step>
-      <step>Click "Save".</step>
-      <step>Perform asserts</step>
-    </steps>
-  </testcase>
-  <testcase>
-    <id>MTA-16</id>
-    <ticketId>MTA-16</ticketId>
-    <name>CreateVirtualProductEntityTest</name>
-    <description>Test Creation for CreateVirtualProductEntity</description>
-    <module>Catalog</module>
-    <components>
-      <component>Virtual Product (CS)</component>
-    </components>
-    <steps>
-      <step>Login as admin.</step>
-      <step>Navigate to the Products &gt; Inventory &gt; Catalog.</step>
-      <step>Click on "+" dropdown and select Virtual Product type.</step>
-      <step>Fill in all data according to data set.</step>
-      <step>Save product.</step>
-      <step>Verify created product.</step>
+      <step/>
+      <step>*Steps:*</step>
+      <step> Log in as default admin user.</step>
+      <step> Go to Stores &gt; Taxes &gt; Tax Zones and Rates.</step>
+      <step> Click 'Add New Tax Rate' button.</step>
+      <step> Fill in data according to dataSet</step>
+      <step> Save Tax Rate.</step>
+      <step> Perform all assertions.</step>
     </steps>
   </testcase>
   <testcase>
@@ -166,4 +74,26 @@
     <step> Verify created product.</step>
     </steps>
   </testcase>
+  <testcase>
+    <id>MTA-93</id>
+    <ticketId>MTA-93</ticketId>
+    <name>AdvancedSearchEntityTest</name>
+    <description>Test Creation for AdvancedSearchEntity</description>
+    <module>CatalogSearch</module>
+    <components>
+      <component>Search Frontend (MX)</component>
+    </components>
+    <steps>
+      <step/>
+      <step>*Preconditions:*</step>
+      <step> Two specific simple product is created(unique sku,name,short/full description, tax class)</step>
+      <step/>
+      <step>Steps</step>
+      <step>Navigate to Frontend</step>
+      <step>Click "Advanced Search"</step>
+      <step>Fill test data in to field(s)</step>
+      <step>Click "Search" button</step>
+      <step>Perform all asserts</step>
+    </steps>
+  </testcase>
 </testcases>
diff --git a/dev/tests/functional/phpunit.xml.dist b/dev/tests/functional/phpunit.xml.dist
index 426c8d02ace..4c50e1d1b00 100755
--- a/dev/tests/functional/phpunit.xml.dist
+++ b/dev/tests/functional/phpunit.xml.dist
@@ -41,6 +41,7 @@
                 <object class="Mtf\System\Isolation\Driver\Base"/>
             </arguments>
         </listener>
+        <listener class="Mtf\System\Event\StateListener"/>
     </listeners>
 
     <php>
@@ -51,6 +52,8 @@
         <env name="isolation_config_path" value="config/isolation.yml.dist"/>
         <env name="handlers_config_path" value="config/handler.yml.dist"/>
         <env name="configuration:Mtf/TestSuite/InjectableTests" value="basic"/>
+        <env name="log_directory" value="var/log"/>
+        <env name="events_preset" value="base"/>
     </php>
 
 </phpunit>
diff --git a/dev/tests/functional/tests/app/Magento/Backend/Test/Block/FormPageActions.php b/dev/tests/functional/tests/app/Magento/Backend/Test/Block/FormPageActions.php
index 92a90eab91c..636a537ea74 100644
--- a/dev/tests/functional/tests/app/Magento/Backend/Test/Block/FormPageActions.php
+++ b/dev/tests/functional/tests/app/Magento/Backend/Test/Block/FormPageActions.php
@@ -126,4 +126,14 @@ class FormPageActions extends PageActions
         $this->_rootElement->find($this->deleteButton)->click();
         $this->_rootElement->acceptAlert();
     }
+
+    /**
+     * Check 'Delete' button availability
+     *
+     * @return bool
+     */
+    public function checkDeleteButton()
+    {
+        return $this->_rootElement->find($this->deleteButton)->isVisible();
+    }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Backend/Test/Block/Widget/FormTabs.php b/dev/tests/functional/tests/app/Magento/Backend/Test/Block/Widget/FormTabs.php
index 1a2bc9ce0fe..f8c59b083ea 100644
--- a/dev/tests/functional/tests/app/Magento/Backend/Test/Block/Widget/FormTabs.php
+++ b/dev/tests/functional/tests/app/Magento/Backend/Test/Block/Widget/FormTabs.php
@@ -118,10 +118,23 @@ class FormTabs extends Form
     public function fill(FixtureInterface $fixture, Element $element = null)
     {
         $tabs = $this->getFieldsByTabs($fixture);
+        return $this->fillTabs($tabs, $element);
+    }
+
+    /**
+     * Fill specified form with tabs
+     *
+     * @param array $tabs
+     * @param Element|null $element
+     * @return FormTabs
+     */
+    protected function fillTabs(array $tabs, Element $element = null)
+    {
+        $context = ($element === null) ? $this->_rootElement : $element;
         foreach ($tabs as $tabName => $tabFields) {
             $tabElement = $this->getTabElement($tabName);
             $this->openTab($tabName);
-            $tabElement->fillFormTab(array_merge($tabFields, $this->unassignedFields), $this->_rootElement);
+            $tabElement->fillFormTab(array_merge($tabFields, $this->unassignedFields), $context);
             $this->updateUnassignedFields($tabElement);
         }
         if (!empty($this->unassignedFields)) {
diff --git a/dev/tests/functional/tests/app/Magento/Backend/Test/Block/Widget/Grid.php b/dev/tests/functional/tests/app/Magento/Backend/Test/Block/Widget/Grid.php
index 7d9b5ba2168..2a7b67f0d4e 100644
--- a/dev/tests/functional/tests/app/Magento/Backend/Test/Block/Widget/Grid.php
+++ b/dev/tests/functional/tests/app/Magento/Backend/Test/Block/Widget/Grid.php
@@ -280,17 +280,22 @@ abstract class Grid extends Block
      *
      * @param array $filter
      * @param bool $isSearchable
+     * @param bool $isStrict
      * @return Element
      */
-    protected function getRow(array $filter, $isSearchable = true)
+    protected function getRow(array $filter, $isSearchable = true, $isStrict = true)
     {
         if ($isSearchable) {
             $this->search($filter);
         }
         $location = '//div[@class="grid"]//tr[';
+        $rowTemplate = 'td[contains(text(),normalize-space("%s"))]';
+        if ($isStrict) {
+            $rowTemplate = 'td[text()[normalize-space()="%s"]]';
+        }
         $rows = [];
         foreach ($filter as $value) {
-            $rows[] = 'td[text()[normalize-space()="' . $value . '"]]';
+            $rows[] = sprintf($rowTemplate, $value);
         }
         $location = $location . implode(' and ', $rows) . ']';
         return $this->_rootElement->find($location, Locator::SELECTOR_XPATH);
@@ -301,11 +306,12 @@ abstract class Grid extends Block
      *
      * @param array $filter
      * @param bool $isSearchable
+     * @param bool $isStrict
      * @return bool
      */
-    public function isRowVisible(array $filter, $isSearchable = true)
+    public function isRowVisible(array $filter, $isSearchable = true, $isStrict = true)
     {
-        return $this->getRow($filter, $isSearchable)->isVisible();
+        return $this->getRow($filter, $isSearchable, $isStrict)->isVisible();
     }
 
     /**
@@ -321,5 +327,6 @@ abstract class Grid extends Block
             $sortBlock->click();
             $this->getTemplateBlock()->waitLoader();
         }
+        $this->reinitRootElement();
     }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Backend/Test/Handler/Conditions.php b/dev/tests/functional/tests/app/Magento/Backend/Test/Handler/Conditions.php
new file mode 100644
index 00000000000..2c04739f4b3
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Backend/Test/Handler/Conditions.php
@@ -0,0 +1,281 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Backend\Test\Handler;
+
+use Mtf\Fixture\FixtureInterface;
+use Mtf\Handler\Curl;
+
+/**
+ * Class Conditions
+ * Curl class for fixture with conditions
+ *
+ * Format value of conditions.
+ * Add slash to symbols: "{", "}", "[", "]", ":".
+ * 1. Single condition:
+ * [Type|Param|Param|...|Param]
+ * 2. List conditions:
+ * [Type|Param|Param|...|Param]
+ * [Type|Param|Param|...|Param]
+ * [Type|Param|Param|...|Param]
+ * 3. Combination condition with single condition
+ * {Type|Param|Param|...|Param:[Type|Param|Param|...|Param]}
+ * 4. Combination condition with list conditions
+ * {Type|Param|Param|...|Param:[[Type|Param|...|Param][Type|Param|...|Param]...[Type|Param|...|Param]]}
+ *
+ * Example value:
+ * {Products subselection|total amount|greater than|135|ANY:[[Price in cart|is|100][Quantity in cart|is|100]]}
+ * {Conditions combination:[
+ *     [Subtotal|is|100]
+ *     {Product attribute combination|NOT FOUND|ANY:[[Attribute Set|is|Default][Attribute Set|is|Default]]}
+ * ]}
+ */
+abstract class Conditions extends Curl
+{
+    /**
+     * Map of type parameter
+     *
+     * @var array
+     */
+    protected $mapTypeParams = [];
+
+    /**
+     * Map of rule parameters
+     *
+     * @var array
+     */
+    protected $mapRuleParams = [
+        'operator' => [
+            'is' => '==',
+            'is not' => '!=',
+            'equal to' => '==',
+        ],
+        'value_type' => [
+            'same_as' => 'the Same as Matched Product Categories',
+        ],
+        'value' => [
+            'California' => '12',
+            'United States' => 'US',
+            '[flatrate] Fixed' => 'flatrate_flatrate',
+        ],
+        'aggregator' => [
+            'ALL' => 'all',
+        ],
+    ];
+
+    /**
+     * Map encode special chars
+     *
+     * @var array
+     */
+    protected $encodeChars = [
+        '\{' => '&lbrace;',
+        '\}' => '&rbrace;',
+        '\[' => '&lbracket;',
+        '\]' => '&rbracket;',
+        '\:' => '&colon;',
+    ];
+
+    /**
+     * Map decode special chars
+     *
+     * @var array
+     */
+    protected $decodeChars = [
+        '&lbrace;' => '{',
+        '&rbrace;' => '}',
+        '&lbracket;' => '[',
+        '&rbracket;' => ']',
+        '&colon;' => ':',
+    ];
+
+    /**
+     * Prepare conditions to array for send by post request
+     *
+     * @param string $conditions
+     * @return array
+     */
+    protected function prepareCondition($conditions)
+    {
+        $conditions = $this->decodeValue($conditions);
+        $defaultCondition = [
+            1 => [
+                'type' => 'Magento\SalesRule\Model\Rule\Condition\Combine',
+                'aggregator' => 'all',
+                'value' => '1'
+            ]
+        ];
+        return $defaultCondition + $this->convertMultipleCondition($conditions);
+    }
+
+    /**
+     * Convert condition combination
+     *
+     * @param string $combination
+     * @param array|string $conditions
+     * @param int $nesting
+     * @return array
+     */
+    private function convertConditionsCombination($combination, $conditions, $nesting)
+    {
+        $combination = [$nesting => $this->convertSingleCondition($combination)];
+        $conditions = $this->convertMultipleCondition($conditions, $nesting);
+        return $combination + $conditions;
+    }
+
+    /**
+     * Convert multiple condition
+     *
+     * @param array $conditions
+     * @param int $nesting
+     * @param int $count
+     * @return array
+     */
+    private function convertMultipleCondition(array $conditions, $nesting = 1, $count = 1)
+    {
+        $result = [];
+        foreach ($conditions as $key => $condition) {
+            if (!is_numeric($key)) {
+                $nesting = $nesting . '--' . $count;
+                $result += $this->convertConditionsCombination($key, $condition, $nesting);
+            } elseif (is_string($condition)) {
+                $result[$nesting . '--' . $count] = $this->convertSingleCondition($condition);
+            } else {
+                $result += $this->convertMultipleCondition($condition, $nesting, $count);
+            }
+            $count++;
+        }
+        return $result;
+    }
+
+    /**
+     * Convert single condition
+     *
+     * @param string $condition
+     * @return array
+     * @throws \Exception
+     */
+    private function convertSingleCondition($condition)
+    {
+        $condition = $this->parseCondition($condition);
+        extract($condition);
+
+        $typeParam = $this->getTypeParam($type);
+        if (empty($typeParam)) {
+            throw new \Exception("Can't find type param \"{$type}\".");
+        }
+
+        $ruleParam = [];
+        foreach ($rules as $value) {
+            $param = $this->getRuleParam($value);
+            if (empty($param)) {
+                $ruleParam['value'] = $value;
+                break;
+            }
+            $ruleParam += $param;
+        }
+        if (count($ruleParam) != count($rules)) {
+            throw new \Exception(
+                "Can't find all params. "
+                . "\nSearch: " . implode(', ', $rules) . " "
+                . "\nFind: " . implode(', ', $ruleParam)
+            );
+        }
+
+        return $typeParam + $ruleParam;
+    }
+
+    /**
+     * Get type param by name
+     *
+     * @param string $name
+     * @return array
+     */
+    private function getTypeParam($name)
+    {
+        return isset($this->mapTypeParams[$name]) ? $this->mapTypeParams[$name] : [];
+    }
+
+    /**
+     * Get rule param by name
+     *
+     * @param string $name
+     * @return array
+     */
+    private function getRuleParam($name)
+    {
+        foreach ($this->mapRuleParams as $typeParam => &$params) {
+            if (isset($params[$name])) {
+                return [$typeParam => $params[$name]];
+            }
+        }
+        return [];
+    }
+
+    /**
+     * Decode value
+     *
+     * @param string $value
+     * @return array
+     * @throws \Exception
+     */
+    private function decodeValue($value)
+    {
+        $value = str_replace(array_keys($this->encodeChars), $this->encodeChars, $value);
+        $value = preg_replace('/(\]|})({|\[)/', '$1,$2', $value);
+        $value = preg_replace('/{([^:]+):/', '{"$1":', $value);
+        $value = preg_replace('/\[([^\[{])/', '"$1', $value);
+        $value = preg_replace('/([^\]}])\]/', '$1"', $value);
+        $value = str_replace(array_keys($this->decodeChars), $this->decodeChars, $value);
+
+        $value = "[{$value}]";
+        $value = json_decode($value, true);
+        if (null === $value) {
+            throw new \Exception('Bad format value.');
+        }
+        return $value;
+    }
+
+    /**
+     * Parse condition
+     *
+     * @param string $condition
+     * @return array
+     * @throws \Exception
+     */
+    private function parseCondition($condition)
+    {
+        if (!preg_match_all('/([^|]+\|?)/', $condition, $match)) {
+            throw new \Exception('Bad format condition');
+        }
+        foreach ($match[1] as $key => $value) {
+            $match[1][$key] = rtrim($value, '|');
+        }
+
+        return [
+            'type' => array_shift($match[1]),
+            'rules' => array_values($match[1]),
+        ];
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Backend/Test/Handler/Pagination.php b/dev/tests/functional/tests/app/Magento/Backend/Test/Handler/Pagination.php
deleted file mode 100644
index 1f8a1b06c6b..00000000000
--- a/dev/tests/functional/tests/app/Magento/Backend/Test/Handler/Pagination.php
+++ /dev/null
@@ -1,85 +0,0 @@
-<?php
-/**
- * Magento
- *
- * NOTICE OF LICENSE
- *
- * This source file is subject to the Open Software License (OSL 3.0)
- * that is bundled with this package in the file LICENSE.txt.
- * It is also available through the world-wide-web at this URL:
- * http://opensource.org/licenses/osl-3.0.php
- * If you did not receive a copy of the license and are unable to
- * obtain it through the world-wide-web, please send an email
- * to license@magentocommerce.com so we can send you a copy immediately.
- *
- * DISCLAIMER
- *
- * Do not edit or add to this file if you wish to upgrade Magento to newer
- * versions in the future. If you wish to customize Magento for your
- * needs please refer to http://www.magentocommerce.com for more information.
- *
- * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
- * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
- */
-
-namespace Magento\Backend\Test\Handler;
-
-use Mtf\Util\Protocol\CurlInterface;
-use Mtf\Util\Protocol\CurlTransport;
-use Mtf\Util\Protocol\CurlTransport\BackendDecorator;
-use Mtf\System\Config;
-
-/**
- * Class Pagination
- * Used to omit possible issue, when searched Id is not on the same page in cURL response
- */
-class Pagination
-{
-    /**
-     * Pattern for searching grid table in cURL response
-     *
-     * @var string
-     */
-    protected $regExpPattern;
-
-    /**
-     * Url of cURL request
-     *
-     * @var string
-     */
-    protected $url;
-
-    /**
-     * Setting all Pagination params for Pagination object.
-     * Required url for cURL request and regexp pattern for searching in cURL response.
-     *
-     * @param $url
-     * @param $regExpPattern
-     */
-    public function __construct($url, $regExpPattern)
-    {
-        $this->url = $url;
-        $this->regExpPattern = $regExpPattern;
-    }
-
-    /**
-     * Retrieves id from cURL response
-     *
-     * @throws \Exception
-     * @return mixed
-     */
-    public function getId()
-    {
-        $url = $_ENV['app_backend_url'] . $this->url;
-        $curl = new BackendDecorator(new CurlTransport(), new Config);
-        $curl->addOption(CURLOPT_HEADER, 1);
-        $curl->write(CurlInterface::POST, $url, '1.0');
-        $response = $curl->read();
-        $curl->close();
-        preg_match($this->regExpPattern, $response, $matches);
-        if (empty($matches)) {
-            throw new \Exception('Cannot find id');
-        }
-        return $matches[1];
-    }
-}
diff --git a/dev/tests/functional/tests/app/Magento/Bundle/Test/Block/Adminhtml/Product/Form.xml b/dev/tests/functional/tests/app/Magento/Bundle/Test/Block/Adminhtml/Product/ProductForm.xml
similarity index 100%
rename from dev/tests/functional/tests/app/Magento/Bundle/Test/Block/Adminhtml/Product/Form.xml
rename to dev/tests/functional/tests/app/Magento/Bundle/Test/Block/Adminhtml/Product/ProductForm.xml
diff --git a/dev/tests/functional/tests/app/Magento/Bundle/Test/Fixture/CatalogProductBundle.php b/dev/tests/functional/tests/app/Magento/Bundle/Test/Fixture/CatalogProductBundle.php
index 6e5a7bf751e..ff1f13a2449 100644
--- a/dev/tests/functional/tests/app/Magento/Bundle/Test/Fixture/CatalogProductBundle.php
+++ b/dev/tests/functional/tests/app/Magento/Bundle/Test/Fixture/CatalogProductBundle.php
@@ -29,6 +29,7 @@ use Mtf\Handler\HandlerFactory;
 use Mtf\Fixture\FixtureFactory;
 use Mtf\Fixture\InjectableFixture;
 use Mtf\Repository\RepositoryFactory;
+use Mtf\System\Event\EventManagerInterface;
 
 /**
  * Class CatalogProductBundle
@@ -53,6 +54,7 @@ class CatalogProductBundle extends InjectableFixture
      * @param RepositoryFactory $repositoryFactory
      * @param FixtureFactory $fixtureFactory
      * @param HandlerFactory $handlerFactory
+     * @param EventManagerInterface $eventManager
      * @param array $data
      * @param string $dataSet
      * @param bool $persist
@@ -62,6 +64,7 @@ class CatalogProductBundle extends InjectableFixture
         RepositoryFactory $repositoryFactory,
         FixtureFactory $fixtureFactory,
         HandlerFactory $handlerFactory,
+        EventManagerInterface $eventManager,
         array $data = [],
         $dataSet = '',
         $persist = false
@@ -74,6 +77,7 @@ class CatalogProductBundle extends InjectableFixture
             $repositoryFactory,
             $fixtureFactory,
             $handlerFactory,
+            $eventManager,
             $data,
             $dataSet,
             $persist
@@ -466,6 +470,7 @@ class CatalogProductBundle extends InjectableFixture
         'is_required' => '0',
         'default_value' => '2',
         'input' => 'select',
+        'source' => 'Magento\Catalog\Test\Fixture\CatalogProductSimple\TaxClass',
     ];
 
     protected $thumbnail = [
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/Form.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/CategoryForm.php
similarity index 96%
rename from dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/Form.php
rename to dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/CategoryForm.php
index d0619300e58..b899aea1b8c 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/Form.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/CategoryForm.php
@@ -28,11 +28,10 @@ use Mtf\Factory\Factory;
 use Magento\Backend\Test\Block\Widget\FormTabs;
 
 /**
- * Class Form
+ * Class CategoryForm
  * Category container block
- *
  */
-class Form extends FormTabs
+class CategoryForm extends FormTabs
 {
     /**
      * Save button
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/Form.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/CategoryForm.xml
similarity index 76%
rename from dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/Form.xml
rename to dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/CategoryForm.xml
index ca13e666060..5968fa622e4 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/Form.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Category/Edit/CategoryForm.xml
@@ -33,6 +33,7 @@
             <is_active>
                 <input>select</input>
             </is_active>
+            <description />
             <include_in_menu>
                 <input>checkbox</input>
             </include_in_menu>
@@ -50,6 +51,21 @@
             <include_in_menu>
                 <input>checkbox</input>
             </include_in_menu>
+            <available_product_listing_config>
+                <selector>#use_config_group_5available_sort_by</selector>
+                <input>checkbox</input>
+            </available_product_listing_config>
+            <available_sort_by>
+                <selector>#group_5available_sort_by</selector>
+                <input>multiselect</input>
+            </available_sort_by>
+            <default_product_listing_config>
+                <selector>#use_config_group_5default_sort_by</selector>
+                <input>checkbox</input>
+            </default_product_listing_config>
+            <default_sort_by>
+                <input>select</input>
+            </default_sort_by>
         </fields>
     </display_setting>
     <custom_design>
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/Advanced/Result.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/AttributeForm.php
similarity index 76%
rename from dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/Advanced/Result.php
rename to dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/AttributeForm.php
index 3d02bc72de4..246273bad21 100644
--- a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/Advanced/Result.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/AttributeForm.php
@@ -22,18 +22,15 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-namespace Magento\CatalogSearch\Test\Page\Advanced;
+namespace Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Edit;
 
-use Magento\CatalogSearch\Test\Page\CatalogsearchResult;
+use Magento\Backend\Test\Block\Widget\FormTabs;
 
 /**
- * Advanced search result page
- *
+ * Class AttributeForm
+ * Catalog Product Attribute form
  */
-class Result extends CatalogsearchResult
+class AttributeForm extends FormTabs
 {
-    /**
-     * URL for search advanced result page
-     */
-    const MCA = 'catalogsearch/advanced/result';
+    //
 }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/AttributeForm.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/AttributeForm.xml
new file mode 100644
index 00000000000..7aa0f91f53f
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/AttributeForm.xml
@@ -0,0 +1,127 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<tabs>
+    <properties>
+        <class>\Magento\Backend\Test\Block\Widget\Tab</class>
+        <selector>#product_attribute_tabs_main</selector>
+        <strategy>css selector</strategy>
+        <fields>
+            <frontend_label>
+                <selector>[name^='frontend_label']</selector>
+            </frontend_label>
+            <frontend_input>
+                <input>select</input>
+            </frontend_input>
+            <is_required>
+                <input>select</input>
+            </is_required>
+        </fields>
+    </properties>
+    <manage-options>
+        <class>\Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Edit\Tab\Options</class>
+        <selector>#product_attribute_tabs_main</selector>
+        <strategy>css selector</strategy>
+        <fields>
+            <is_default>
+                <selector>[name="default[]"]</selector>
+                <input>checkbox</input>
+            </is_default>
+            <admin>
+                <selector>[name="option[value][option_0][0]"]</selector>
+            </admin>
+            <view>
+                <selector>[name="option[value][option_0][1]"]</selector>
+            </view>
+        </fields>
+    </manage-options>
+    <advanced-properties>
+        <class>\Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Edit\Tab\Advanced</class>
+        <selector>#product_attribute_tabs_main</selector>
+        <strategy>css selector</strategy>
+        <fields>
+            <attribute_code>
+            </attribute_code>
+            <is_global>
+                <input>select</input>
+            </is_global>
+            <default_value_text>
+            </default_value_text>
+            <is_unique>
+                <input>select</input>
+            </is_unique>
+            <is_configurable>
+                <input>select</input>
+            </is_configurable>
+        </fields>
+    </advanced-properties>
+    <manage-labels>
+        <class>\Magento\Backend\Test\Block\Widget\Tab</class>
+        <selector>#product_attribute_tabs_labels</selector>
+        <strategy>css selector</strategy>
+        <fields>
+            <manage_frontend_label>
+                <selector>[name^='frontend_label']</selector>
+            </manage_frontend_label>
+        </fields>
+    </manage-labels>
+    <frontend-properties>
+        <class>\Magento\Backend\Test\Block\Widget\Tab</class>
+        <selector>#product_attribute_tabs_front</selector>
+        <strategy>css selector</strategy>
+        <fields>
+            <is_searchable>
+                <input>select</input>
+            </is_searchable>
+            <is_visible_in_advanced_search>
+                <input>select</input>
+            </is_visible_in_advanced_search>
+            <is_comparable>
+                <input>select</input>
+            </is_comparable>
+            <is_filterable>
+                <input>select</input>
+            </is_filterable>
+            <is_filterable_in_search>
+                <input>select</input>
+            </is_filterable_in_search>
+            <is_used_for_promo_rules>
+                <input>select</input>
+            </is_used_for_promo_rules>
+            <is_html_allowed_on_front>
+                <input>select</input>
+            </is_html_allowed_on_front>
+            <is_visible_on_front>
+                <input>select</input>
+            </is_visible_on_front>
+            <used_in_product_listing>
+                <input>select</input>
+            </used_in_product_listing>
+            <used_for_sort_by>
+                <input>select</input>
+            </used_for_sort_by>
+        </fields>
+    </frontend-properties>
+</tabs>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Advanced.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Advanced.php
new file mode 100644
index 00000000000..3f94fee30d3
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Advanced.php
@@ -0,0 +1,65 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Edit\Tab;
+
+use Mtf\Client\Element;
+use Magento\Backend\Test\Block\Widget\Tab;
+
+/**
+ * Class AdvancedPropertiesTab
+ * Tab "Advanced Attribute Properties"
+ */
+class Advanced extends Tab
+{
+    /**
+     * "Advanced Attribute Properties" tab-button
+     *
+     * @var string
+     */
+    protected $propertiesTab = '[data-target="#advanced_fieldset-content"][data-toggle="collapse"]';
+
+    /**
+     * "Advanced Attribute Properties" tab-button active
+     *
+     * @var string
+     */
+    protected $propertiesTabActive = '.title.active';
+
+    /**
+     * Fill 'Advanced Attribute Properties' tab
+     *
+     * @param array $fields
+     * @param Element|null $element
+     * @return $this
+     */
+    public function fillFormTab(array $fields, Element $element = null)
+    {
+        if (!$this->_rootElement->find($this->propertiesTabActive)->isVisible()) {
+            $this->_rootElement->find($this->propertiesTab)->click();
+        }
+
+        return parent::fillFormTab($fields);
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options.php
new file mode 100644
index 00000000000..b2b2b1d91d1
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options.php
@@ -0,0 +1,61 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Edit\Tab;
+
+use Mtf\Client\Element;
+use Magento\Backend\Test\Block\Widget\Tab;
+
+/**
+ * Class Options
+ * Options form
+ */
+class Options extends Tab
+{
+    /**
+     * 'Add Option' button
+     *
+     * @var string
+     */
+    protected $addOption = '#add_new_option_button';
+
+    /**
+     * Fill 'Options' tab
+     *
+     * @param array $fields
+     * @param Element|null $element
+     * @return $this
+     */
+    public function fillFormTab(array $fields, Element $element = null)
+    {
+        foreach ($fields['options']['value'] as $field) {
+            $this->_rootElement->find($this->addOption)->click();
+            $this->blockFactory->create(
+                'Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Edit\Tab\Options\Option',
+                ['element' => $this->_rootElement->find('.ui-sortable tr:nth-child(1)')]
+            )->fillOptions($field);
+        }
+        return $this;
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options/Option.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options/Option.php
new file mode 100644
index 00000000000..f50cb6b2da1
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options/Option.php
@@ -0,0 +1,46 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Edit\Tab\Options;
+
+use Mtf\Block\Form;
+
+/**
+ * Class Option
+ * Form "Option" on tab "Manage Options"
+ */
+class Option extends Form
+{
+    /**
+     * Fill the form
+     *
+     * @param array $fields
+     * @return void
+     */
+    public function fillOptions(array $fields)
+    {
+        $data = $this->dataMapping($fields);
+        $this->_fill($data);
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options/Option.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options/Option.xml
new file mode 100644
index 00000000000..dee0b7f0941
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Edit/Tab/Options/Option.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<mapping strict="0">
+    <fields>
+        <is_default>
+            <selector>[name="default[]"]</selector>
+            <input>checkbox</input>
+        </is_default>
+        <admin>
+            <selector>[name="option[value][option_0][0]"]</selector>
+        </admin>
+        <view>
+            <selector>[name="option[value][option_0][1]"]</selector>
+        </view>
+    </fields>
+</mapping>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Grid.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Grid.php
new file mode 100644
index 00000000000..ce938b54e42
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Attribute/Grid.php
@@ -0,0 +1,57 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Block\Adminhtml\Product\Attribute;
+
+use Mtf\Client\Element;
+use Magento\Backend\Test\Block\Widget\Grid as AbstractGrid;
+
+/**
+ * Class Grid
+ * Attribute grid of Product Attributes
+ */
+class Grid extends AbstractGrid
+{
+    /**
+     * Locator value for link in action column
+     *
+     * @var string
+     */
+    protected $editLink = 'td.col-frontend_label';
+
+    /**
+     * Filters array mapping
+     *
+     * @var array
+     */
+    protected $filters = [
+        'attribute_code' => [
+            'selector' => 'input[name="attribute_code"]'
+        ],
+        'is_user_defined' => [
+            'selector' => 'select[name="is_user_defined"]',
+            'input' => 'select'
+        ],
+    ];
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Form.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/ProductForm.php
similarity index 92%
rename from dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Form.php
rename to dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/ProductForm.php
index c1694c281b9..274a2276817 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Form.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/ProductForm.php
@@ -28,33 +28,19 @@ use Mtf\Client\Element;
 use Mtf\Factory\Factory;
 use Mtf\Client\Element\Locator;
 use Mtf\Fixture\FixtureInterface;
+use Mtf\Fixture\InjectableFixture;
 use Magento\Catalog\Test\Fixture\Product;
 use Magento\Backend\Test\Block\Widget\Tab;
 use Magento\Backend\Test\Block\Widget\FormTabs;
 use Magento\Catalog\Test\Fixture\ConfigurableProduct;
-use Magento\Catalog\Test\Fixture\CatalogCategoryEntity;
-use Mtf\Fixture\InjectableFixture;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 
 /**
  * Class ProductForm
  * Product form on backend product page
  */
-class Form extends FormTabs
+class ProductForm extends FormTabs
 {
-    /**
-     * Variations tab selector
-     *
-     * @var string
-     */
-    protected $variationsTab = '[data-ui-id="product-tabs-tab-content-super-config"] .title';
-
-    /**
-     * Variations wrapper selector
-     *
-     * @var string
-     */
-    protected $variationsWrapper = '[data-ui-id="product-tabs-tab-content-super-config"]';
-
     /**
      * New variation set button selector
      *
@@ -100,7 +86,7 @@ class Form extends FormTabs
     /**
      * Category fixture
      *
-     * @var CatalogCategoryEntity
+     * @var CatalogCategory
      */
     protected $category;
 
@@ -108,13 +94,13 @@ class Form extends FormTabs
      * Fill the product form
      *
      * @param FixtureInterface $fixture
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @param Element $element
      * @return $this
      */
     public function fillProduct(
         FixtureInterface $fixture,
-        CatalogCategoryEntity $category = null,
+        CatalogCategory $category = null,
         Element $element = null
     ) {
         $this->category = $category;
@@ -320,4 +306,24 @@ class Form extends FormTabs
 
         return $this;
     }
+
+    /**
+     * Get data of the tabs
+     *
+     * @param FixtureInterface|null $fixture
+     * @param Element|null $element
+     * @return array
+     */
+    public function getData(FixtureInterface $fixture = null, Element $element = null)
+    {
+        $data = parent::getData($fixture);
+        if ($fixture->hasData('status')) {
+            $data['status'] = 'Product offline';
+            if ($this->_rootElement->find(sprintf($this->onlineSwitcher, ':checked'))->isVisible()) {
+                $data['status'] = 'Product online';
+            }
+        }
+
+        return $data;
+    }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Form.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/ProductForm.xml
similarity index 99%
rename from dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Form.xml
rename to dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/ProductForm.xml
index b488bff8a90..1b3b0cd0a9b 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/Form.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Adminhtml/Product/ProductForm.xml
@@ -107,6 +107,7 @@
                 <selector>#short_description</selector>
                 <input>textarea</input>
             </short_description>
+            <url_key></url_key>
         </fields>
     </autosettings>
     <variations>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Category/View.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Category/View.php
new file mode 100644
index 00000000000..4b5a13b3108
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Category/View.php
@@ -0,0 +1,51 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Block\Category;
+
+use Mtf\Block\Block;
+
+/**
+ * Class View
+ * Category view block on the category page
+ */
+class View extends Block
+{
+    /**
+     * Description CSS selector
+     *
+     * @var string
+     */
+    protected $description = '.category.description';
+
+    /**
+     * Get description
+     *
+     * @return string
+     */
+    public function getDescription()
+    {
+        return $this->_rootElement->find($this->description)->getText();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ListProduct.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ListProduct.php
index 838888f3db3..6791f38620a 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ListProduct.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ListProduct.php
@@ -61,7 +61,7 @@ class ListProduct extends Block
      *
      * @var string
      */
-    protected $productTitle = '.product.name';
+    protected $productTitle = '.product.name [title="%s"]';
 
     /**
      * Click for Price link on category page
@@ -84,6 +84,13 @@ class ListProduct extends Block
      */
     protected $addToCard = "button.action.tocart";
 
+    /**
+     * Price box CSS selector
+     * 
+     * @var string
+     */
+    protected $priceBox = '.price-box #product-price-%s .price';
+
     /**
      * This method returns the price box block for the named product.
      *
@@ -101,7 +108,6 @@ class ListProduct extends Block
      * Check if product with specified name is visible
      *
      * @param string $productName
-     *
      * @return bool
      */
     public function isProductVisible($productName)
@@ -123,6 +129,7 @@ class ListProduct extends Block
      * Open product view page by clicking on product name
      *
      * @param string $productName
+     * @return void
      */
     public function openProductViewPage($productName)
     {
@@ -133,7 +140,6 @@ class ListProduct extends Block
      * This method returns the element representing the product details for the named product.
      *
      * @param string $productName String containing the name of the product
-     *
      * @return Element
      */
     protected function getProductDetailsElement($productName)
@@ -148,25 +154,17 @@ class ListProduct extends Block
      * This method returns the element on the page associated with the product name.
      *
      * @param string $productName String containing the name of the product
-     *
      * @return Element
      */
     protected function getProductNameElement($productName)
     {
-        return $this->_rootElement->find(
-            $this->productTitle,
-            Locator::SELECTOR_CSS
-        )->find(
-            '//*[@title="' . $productName . '"]',
-            Locator::SELECTOR_XPATH
-        );
+        return $this->_rootElement->find(sprintf($this->productTitle, $productName));
     }
 
     /**
      * Open MAP block on category page
      *
-     * @param $productName
-     *
+     * @param string $productName
      * @return void
      */
     public function openMapBlockOnCategoryPage($productName)
@@ -188,15 +186,12 @@ class ListProduct extends Block
      * Retrieve product price by specified Id
      *
      * @param int $productId
-     *
      * @return string
      */
     public function getPrice($productId)
     {
-        return $this->_rootElement->find(
-            '.price-box #product-price-' . $productId . ' .price',
-            Locator::SELECTOR_CSS
-        )->getText();
+        return $this->_rootElement->find(sprintf($this->priceBox, $productId), Locator::SELECTOR_CSS)
+            ->getText();
     }
 
     /**
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ProductList/Crosssell.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ProductList/Crosssell.php
index 3793f429641..9c7056b9d07 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ProductList/Crosssell.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ProductList/Crosssell.php
@@ -28,6 +28,9 @@ use Mtf\Block\Block;
 use Mtf\Client\Element;
 use Mtf\Client\Element\Locator;
 use \Magento\Catalog\Test\Fixture\Product;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Mtf\Fixture\FixtureInterface;
+use Mtf\Fixture\InjectableFixture;
 
 /**
  * Class Crosssell
@@ -45,15 +48,17 @@ class Crosssell extends Block
     /**
      * Verify cross-sell item
      *
-     * @param Product $crosssell
+     * @param FixtureInterface $crosssell
      * @return bool
      */
-    public function verifyProductCrosssell(Product $crosssell)
+    public function verifyProductCrosssell(FixtureInterface $crosssell)
     {
-        $match = $this->_rootElement->find(
-            sprintf($this->linkSelector, $crosssell->getProductName()),
-            Locator::SELECTOR_CSS
-        );
+        $productName = ($crosssell instanceof InjectableFixture)
+            /** @var CatalogProductSimple $crosssell */
+            ? $crosssell->getName()
+            /** @var Product $crosssell */
+            : $crosssell->getProductName();
+        $match = $this->_rootElement->find(sprintf($this->linkSelector, $productName), Locator::SELECTOR_CSS);
         return $match->isVisible();
     }
 
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ProductList/Toolbar.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ProductList/Toolbar.php
index 8bbdb92f1e0..ff9eeaae543 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ProductList/Toolbar.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/ProductList/Toolbar.php
@@ -39,6 +39,13 @@ class Toolbar extends Block
      */
     protected $nextPageSelector = '.item.current + .item a';
 
+    /**
+     * Selector for "sort by" element
+     *
+     * @var string
+     */
+    protected $sorter = '#sorter';
+
     /**
      * Go to the next page
      *
@@ -54,4 +61,25 @@ class Toolbar extends Block
 
         return false;
     }
+
+    /**
+     * Get method of sorting product
+     *
+     * @return array|string
+     */
+    public function getSelectSortType()
+    {
+        return $this->_rootElement->find($this->sorter)->getValue();
+    }
+
+    /**
+     * Get all available method of sorting product
+     *
+     * @return array|string
+     */
+    public function getSortType()
+    {
+        $content = str_replace("\r", '', $this->_rootElement->find($this->sorter)->getText());
+        return explode("\n", $content);
+    }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/View.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/View.php
index eb37a68a232..8b5df2cbb41 100755
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/View.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Product/View.php
@@ -44,6 +44,13 @@ class View extends Block
      */
     protected $addToCart = '#product-addtocart-button';
 
+    /**
+     * Quantity input id
+     *
+     * @var string
+     */
+    protected $qty = '#qty';
+
     /**
      * 'Check out with PayPal' button
      *
@@ -191,6 +198,18 @@ class View extends Block
         $this->_rootElement->find($this->addToCart, Locator::SELECTOR_CSS)->click();
     }
 
+    /**
+     * Set quantity and click add to cart
+     *
+     * @param int $qty
+     * @return void
+     */
+    public function setQtyAndClickAddToCart($qty)
+    {
+        $this->_rootElement->find($this->qty, Locator::SELECTOR_CSS)->setValue($qty);
+        $this->clickAddToCart();
+    }
+
     /**
      * Find Add To Cart button
      *
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Search.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Search.php
index ec26a9203f0..5313e5ccb79 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Search.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Block/Search.php
@@ -68,6 +68,13 @@ class Search extends Block
      */
     protected $placeholder = '//input[@id="search" and contains(@placeholder, "%s")]';
 
+    /**
+     * Css selector advanced search button
+     *
+     * @var string
+     */
+    protected $advancedSearchSelector = '.action.advanced';
+
     /**
      * Search products by a keyword
      *
@@ -120,8 +127,21 @@ class Search extends Block
             $searchAutocomplete .= sprintf($this->searchItemAmount, $amount);
         }
 
-        $this->waitForElementVisible($searchAutocomplete, Locator::SELECTOR_XPATH);
-        return $this->_rootElement->find($searchAutocomplete, Locator::SELECTOR_XPATH)
-            ->isVisible();
+        $rootElement = $this->_rootElement;
+        return (bool)$this->_rootElement->waitUntil(
+            function () use ($rootElement, $searchAutocomplete) {
+                return $rootElement->find($searchAutocomplete, Locator::SELECTOR_XPATH)->isVisible() ? true : null;
+            }
+        );
+    }
+
+    /**
+     * Click advanced search button
+     *
+     * @return void
+     */
+    public function clickAdvancedSearchButton()
+    {
+        $this->_rootElement->find($this->advancedSearchSelector)->click();
     }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAbsenceDeleteAttributeButton.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAbsenceDeleteAttributeButton.php
new file mode 100644
index 00000000000..2fc4f85c464
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAbsenceDeleteAttributeButton.php
@@ -0,0 +1,66 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Catalog\Test\Page\Adminhtml\CatalogProductAttributeNew;
+
+/**
+ * Class AssertAbsenceDeleteAttributeButton
+ * Checks the button "Delete Attribute" on the Attribute page
+ */
+class AssertAbsenceDeleteAttributeButton extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'high';
+
+    /**
+     * Assert that Delete Attribute button is absent for system attribute on attribute edit page.
+     *
+     * @param CatalogProductAttributeNew $attributeNew
+     * @return void
+     */
+    public function processAssert(CatalogProductAttributeNew $attributeNew)
+    {
+        \PHPUnit_Framework_Assert::assertFalse(
+            $attributeNew->getPageActions()->checkDeleteButton(),
+            "Button 'Delete Attribute' is present on Attribute page"
+        );
+    }
+
+    /**
+     * Text absent button "Delete Attribute" on the Attribute page
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return "Button 'Delete Attribute' is absent on Attribute Page.";
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeOnAttributeForm.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeOnAttributeForm.php
new file mode 100644
index 00000000000..89b4ead34a7
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeOnAttributeForm.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertAttributeOnAttributeForm
+ */
+class AssertAttributeOnAttributeForm extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeOptionsOnProductForm.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeOptionsOnProductForm.php
new file mode 100644
index 00000000000..e42da48c5e8
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeOptionsOnProductForm.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertAttributeOptionsOnProductForm
+ */
+class AssertAttributeOptionsOnProductForm extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeSearchableByLabel.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeSearchableByLabel.php
new file mode 100644
index 00000000000..c770854308d
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertAttributeSearchableByLabel.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertAttributeSearchableByLabel
+ */
+class AssertAttributeSearchableByLabel extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategoryForm.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategoryForm.php
new file mode 100644
index 00000000000..82049f092a2
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategoryForm.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertCategoryForm
+ */
+class AssertCategoryForm extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategoryPage.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategoryPage.php
new file mode 100644
index 00000000000..24c41b9867f
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategoryPage.php
@@ -0,0 +1,150 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Magento\Catalog\Test\Fixture\CatalogCategory;
+use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
+use Mtf\Client\Browser;
+use Mtf\Fixture\FixtureFactory;
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertCategoryPage
+ * Assert that displayed category data on category page equals to passed from fixture
+ */
+class AssertCategoryPage extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * Assert that displayed category data on category page equals to passed from fixture
+     *
+     * @param CatalogCategory $category
+     * @param CatalogCategory $initialCategory
+     * @param FixtureFactory $fixtureFactory
+     * @param CatalogCategoryView $categoryView
+     * @param Browser $browser
+     * @return void
+     */
+    public function processAssert(
+        CatalogCategory $category,
+        CatalogCategory $initialCategory,
+        FixtureFactory $fixtureFactory,
+        CatalogCategoryView $categoryView,
+        Browser $browser
+    ) {
+        $product = $fixtureFactory->createByCode(
+            'catalogProductSimple',
+            [
+                'dataSet' => 'product_without_category',
+                'data' => [
+                    'category_ids' => [
+                        'category' => $initialCategory
+                    ]
+                ]
+            ]
+        );
+        $categoryData = array_merge($initialCategory->getData(), $category->getData());
+        $product->persist();
+        $url = $_ENV['app_frontend_url'] . strtolower($category->getUrlKey()) . '.html';
+        $browser->open($url);
+        \PHPUnit_Framework_Assert::assertEquals(
+            $url,
+            $browser->getUrl(),
+            'Wrong page URL.'
+            . "\nExpected: " . $url
+            . "\nActual: " . $browser->getUrl()
+        );
+
+        if (isset($categoryData['name'])) {
+            $title = $categoryView->getTitleBlock()->getTitle();
+            \PHPUnit_Framework_Assert::assertEquals(
+                $categoryData['name'],
+                $title,
+                'Wrong page title.'
+                . "\nExpected: " . $categoryData['name']
+                . "\nActual: " . $title
+            );
+        }
+
+        if (isset($categoryData['description'])) {
+            $description = $categoryView->getViewBlock()->getDescription();
+            \PHPUnit_Framework_Assert::assertEquals(
+                $categoryData['description'],
+                $description,
+                'Wrong category description.'
+                . "\nExpected: " . $categoryData['description']
+                . "\nActual: " . $description
+            );
+        }
+
+        if (isset($categoryData['default_sort_by'])) {
+            $sortBy = strtolower($categoryData['default_sort_by']);
+            $sortType = $categoryView->getToolbar()->getSelectSortType();
+            \PHPUnit_Framework_Assert::assertEquals(
+                $sortBy,
+                $sortType,
+                'Wrong sorting type.'
+                . "\nExpected: " . $sortBy
+                . "\nActual: " . $sortType
+            );
+        }
+
+        if (isset($categoryData['available_sort_by'])) {
+            $availableSortType = array_filter(
+                $categoryData['available_sort_by'],
+                function (&$value) {
+                    return $value !== '-' && ucfirst($value);
+                }
+            );
+            if ($availableSortType) {
+                $availableSortType = array_values($availableSortType);
+                $availableSortTypeOnPage = $categoryView->getToolbar()->getSortType();
+                \PHPUnit_Framework_Assert::assertEquals(
+                    $availableSortType,
+                    $availableSortTypeOnPage,
+                    'Wrong available sorting type.'
+                    . "\nExpected: " . implode(PHP_EOL, $availableSortType)
+                    . "\nActual: " . implode(PHP_EOL, $availableSortTypeOnPage)
+                );
+            }
+        }
+    }
+
+    /**
+     * Returns a string representation of the object
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Category data on category page equals to passed from fixture.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategorySaveMessage.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategorySaveMessage.php
new file mode 100644
index 00000000000..31f4dfd6856
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCategorySaveMessage.php
@@ -0,0 +1,75 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Magento\Catalog\Test\Page\Adminhtml\CatalogCategoryEdit;
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertCategorySaveMessage
+ * Assert that success message is displayed after category save
+ */
+class AssertCategorySaveMessage extends AbstractConstraint
+{
+    /**
+     * Success category save message
+     */
+    const SUCCESS_MESSAGE = 'You saved the category.';
+
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * Assert that success message is displayed after category save
+     *
+     * @param CatalogCategoryEdit $catalogCategoryEdit
+     * @return void
+     */
+    public function processAssert(CatalogCategoryEdit $catalogCategoryEdit)
+    {
+        $actualMessage = $catalogCategoryEdit->getMessagesBlock()->getSuccessMessages();
+        \PHPUnit_Framework_Assert::assertEquals(
+            self::SUCCESS_MESSAGE,
+            $actualMessage,
+            'Wrong success message is displayed.'
+            . "\nExpected: " . self::SUCCESS_MESSAGE
+            . "\nActual: " . $actualMessage
+        );
+    }
+
+    /**
+     * Success message is displayed
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Success message is displayed.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCrossSellsProductsSection.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCrossSellsProductsSection.php
new file mode 100644
index 00000000000..98f6e122ad7
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertCrossSellsProductsSection.php
@@ -0,0 +1,87 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Cms\Test\Page\CmsIndex;
+use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
+use Magento\Catalog\Test\Page\Product\CatalogProductView;
+use Magento\Checkout\Test\Page\CheckoutCart;
+
+/**
+ * Class AssertCrossSellsProductsSection
+ */
+class AssertCrossSellsProductsSection extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'middle';
+
+    /**
+     * Assert that product is displayed in cross-sell section
+     *
+     * @param CatalogProductSimple $product1
+     * @param CatalogProductSimple $product2
+     * @param CmsIndex $cmsIndex
+     * @param CatalogCategoryView $catalogCategoryView
+     * @param CatalogProductView $catalogProductView
+     * @param CheckoutCart $checkoutCart
+     * @return void
+     */
+    public function processAssert(
+        CatalogProductSimple $product1,
+        CatalogProductSimple $product2,
+        CmsIndex $cmsIndex,
+        CatalogCategoryView $catalogCategoryView,
+        CatalogProductView $catalogProductView,
+        CheckoutCart $checkoutCart
+    ) {
+        $categoryName = $product1->getCategoryIds()[0]['name'];
+        $checkoutCart->open();
+        $checkoutCart->getCartBlock()->clearShoppingCart();
+        $cmsIndex->getTopmenu()->selectCategoryByName($categoryName);
+        $catalogCategoryView->getListProductBlock()->openProductViewPage($product1->getName());
+        $catalogProductView->getViewBlock()->addToCart($product1);
+
+        \PHPUnit_Framework_Assert::assertTrue(
+            $checkoutCart->getCrosssellBlock()->verifyProductCrosssell($product2),
+            'Product \'' . $product2->getName() . '\' is absent in cross-sell section.'
+        );
+    }
+
+    /**
+     * Text success product is displayed in cross-sell section
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Product is displayed in cross-sell section.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoCrossSellsProductsSection.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoCrossSellsProductsSection.php
new file mode 100644
index 00000000000..f600e90898b
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoCrossSellsProductsSection.php
@@ -0,0 +1,87 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Cms\Test\Page\CmsIndex;
+use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
+use Magento\Catalog\Test\Page\Product\CatalogProductView;
+use Magento\Checkout\Test\Page\CheckoutCart;
+
+/**
+ * Class AssertNoCrossSellsProductsSection
+ */
+class AssertNoCrossSellsProductsSection extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'middle';
+
+    /**
+     * Assert that product is not displayed in cross-sell section
+     *
+     * @param CatalogProductSimple $product1
+     * @param CatalogProductSimple $product2
+     * @param CmsIndex $cmsIndex
+     * @param CatalogCategoryView $catalogCategoryView
+     * @param CatalogProductView $catalogProductView
+     * @param CheckoutCart $checkoutCart
+     * @return void
+     */
+    public function processAssert(
+        CatalogProductSimple $product1,
+        CatalogProductSimple $product2,
+        CmsIndex $cmsIndex,
+        CatalogCategoryView $catalogCategoryView,
+        CatalogProductView $catalogProductView,
+        CheckoutCart $checkoutCart
+    ) {
+        $categoryName = $product1->getCategoryIds()[0]['name'];
+        $checkoutCart->open();
+        $checkoutCart->getCartBlock()->clearShoppingCart();
+        $cmsIndex->getTopmenu()->selectCategoryByName($categoryName);
+        $catalogCategoryView->getListProductBlock()->openProductViewPage($product1->getName());
+        $catalogProductView->getViewBlock()->addToCart($product1);
+
+        \PHPUnit_Framework_Assert::assertFalse(
+            $checkoutCart->getCrosssellBlock()->verifyProductCrosssell($product2),
+            'Product \'' . $product2->getName() . '\' is exist in cross-sell section.'
+        );
+    }
+
+    /**
+     * Text success product is not displayed in cross-sell section
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Product is not displayed in cross-sell section.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoRelatedProductsSection.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoRelatedProductsSection.php
new file mode 100644
index 00000000000..c722951047d
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoRelatedProductsSection.php
@@ -0,0 +1,82 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Cms\Test\Page\CmsIndex;
+use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
+use Magento\Catalog\Test\Page\Product\CatalogProductView;
+
+/**
+ * Class AssertNoRelatedProductsSection
+ */
+class AssertNoRelatedProductsSection extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'middle';
+
+    /**
+     * Assert that product is not displayed in related products section
+     *
+     * @param CatalogProductSimple $product1
+     * @param CatalogProductSimple $product2
+     * @param CmsIndex $cmsIndex
+     * @param CatalogCategoryView $catalogCategoryView
+     * @param CatalogProductView $catalogProductView
+     * @return void
+     */
+    public function processAssert(
+        CatalogProductSimple $product1,
+        CatalogProductSimple $product2,
+        CmsIndex $cmsIndex,
+        CatalogCategoryView $catalogCategoryView,
+        CatalogProductView $catalogProductView
+    ) {
+        $categoryName = $product1->getCategoryIds()[0]['name'];
+        $cmsIndex->open();
+        $cmsIndex->getTopmenu()->selectCategoryByName($categoryName);
+        $catalogCategoryView->getListProductBlock()->openProductViewPage($product1->getName());
+
+        \PHPUnit_Framework_Assert::assertFalse(
+            $catalogProductView->getRelatedProductBlock()->isRelatedProductVisible($product2->getName()),
+            'Product \'' . $product2->getName() . '\' is exist in related products.'
+        );
+    }
+
+    /**
+     * Text success product is not displayed in related products section
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Product is not displayed in related products section.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoUpSellsProductsSection.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoUpSellsProductsSection.php
new file mode 100644
index 00000000000..7aec1213cfe
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertNoUpSellsProductsSection.php
@@ -0,0 +1,82 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Cms\Test\Page\CmsIndex;
+use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
+use Magento\Catalog\Test\Page\Product\CatalogProductView;
+
+/**
+ * Class AssertNoUpSellsProductsSection
+ */
+class AssertNoUpSellsProductsSection extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'middle';
+
+    /**
+     * Assert that product is not displayed in up-sell section
+     *
+     * @param CatalogProductSimple $product1
+     * @param CatalogProductSimple $product2
+     * @param CmsIndex $cmsIndex
+     * @param CatalogCategoryView $catalogCategoryView
+     * @param CatalogProductView $catalogProductView
+     * @return void
+     */
+    public function processAssert(
+        CatalogProductSimple $product1,
+        CatalogProductSimple $product2,
+        CmsIndex $cmsIndex,
+        CatalogCategoryView $catalogCategoryView,
+        CatalogProductView $catalogProductView
+    ) {
+        $categoryName = $product1->getCategoryIds()[0]['name'];
+        $cmsIndex->open();
+        $cmsIndex->getTopmenu()->selectCategoryByName($categoryName);
+        $catalogCategoryView->getListProductBlock()->openProductViewPage($product1->getName());
+
+        \PHPUnit_Framework_Assert::assertFalse(
+            $catalogProductView->getUpsellBlock()->isUpsellProductVisible($product2->getName()),
+            'Product \'' . $product2->getName() . '\' is exist in up-sells products.'
+        );
+    }
+
+    /**
+     * Text success product is not displayed in up-sell section
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Product is not displayed in up-sell section.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeDisplayingOnFrontend.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeDisplayingOnFrontend.php
new file mode 100644
index 00000000000..cc5e69c1441
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeDisplayingOnFrontend.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeDisplayingOnFrontend
+ */
+class AssertProductAttributeDisplayingOnFrontend extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeDisplayingOnSearchForm.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeDisplayingOnSearchForm.php
new file mode 100644
index 00000000000..31015e0658d
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeDisplayingOnSearchForm.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeDisplayingOnSearchForm
+ */
+class AssertProductAttributeDisplayingOnSearchForm extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeInGrid.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeInGrid.php
new file mode 100644
index 00000000000..eebd8dbfc5f
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeInGrid.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeInGrid
+ */
+class AssertProductAttributeInGrid extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsComparable.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsComparable.php
new file mode 100644
index 00000000000..816f31c6652
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsComparable.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeIsComparable
+ */
+class AssertProductAttributeIsComparable extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsFilterable.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsFilterable.php
new file mode 100644
index 00000000000..4d7a040b3b7
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsFilterable.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeIsFilterable
+ */
+class AssertProductAttributeIsFilterable extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsFilterableInSearch.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsFilterableInSearch.php
new file mode 100644
index 00000000000..d1e7e97d89f
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsFilterableInSearch.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeIsFilterableInSearch
+ */
+class AssertProductAttributeIsFilterableInSearch extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsGlobal.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsGlobal.php
new file mode 100644
index 00000000000..39ee8167855
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsGlobal.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeIsGlobal
+ */
+class AssertProductAttributeIsGlobal extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsHtmlAllowed.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsHtmlAllowed.php
new file mode 100644
index 00000000000..3757dbf1f50
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsHtmlAllowed.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeIsHtmlAllowed
+ */
+class AssertProductAttributeIsHtmlAllowed extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsRequired.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsRequired.php
new file mode 100644
index 00000000000..af0ae098b22
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsRequired.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeIsRequired
+ */
+class AssertProductAttributeIsRequired extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsUnique.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsUnique.php
new file mode 100644
index 00000000000..47878c25cda
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsUnique.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeIsUnique
+ */
+class AssertProductAttributeIsUnique extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsUsedPromoRules.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsUsedPromoRules.php
new file mode 100644
index 00000000000..1354a41bec2
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeIsUsedPromoRules.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeIsUsedPromoRules
+ */
+class AssertProductAttributeIsUsedPromoRules extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeOnProductForm.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeOnProductForm.php
new file mode 100644
index 00000000000..74960e44340
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeOnProductForm.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeOnProductForm
+ */
+class AssertProductAttributeOnProductForm extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeSaveMessage.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeSaveMessage.php
new file mode 100644
index 00000000000..ed9f6e0f34f
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeSaveMessage.php
@@ -0,0 +1,70 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Catalog\Test\Page\Adminhtml\CatalogProductAttributeIndex;
+
+/**
+ * Class AssertProductAttributeSaveMessage
+ */
+class AssertProductAttributeSaveMessage extends AbstractConstraint
+{
+    const SUCCESS_MESSAGE = 'You saved the product attribute.';
+
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'high';
+
+    /**
+     * Assert that message "You saved the product attribute." is present on Attribute page
+     *
+     * @param CatalogProductAttributeIndex $attributeIndex
+     * @return void
+     */
+    public function processAssert(CatalogProductAttributeIndex $attributeIndex)
+    {
+        \PHPUnit_Framework_Assert::assertEquals(
+            self::SUCCESS_MESSAGE,
+            $attributeIndex->getMessageBlock()->getSuccessMessages(),
+            'Wrong success message is displayed.'
+            . "\nExpected: " . self::SUCCESS_MESSAGE
+            . "\nActual: " . $attributeIndex->getMessageBlock()->getSuccessMessages()
+        );
+    }
+
+    /**
+     * Text success present save message
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Attribute success save message is present.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeUsedSortOnFrontend.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeUsedSortOnFrontend.php
new file mode 100644
index 00000000000..806412f97d7
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductAttributeUsedSortOnFrontend.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductAttributeUsedSortOnFrontend
+ */
+class AssertProductAttributeUsedSortOnFrontend extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductForm.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductForm.php
index 414472c7caa..7fe6cdba788 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductForm.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductForm.php
@@ -80,8 +80,8 @@ class AssertProductForm extends AbstractConstraint
         $filter = ['sku' => $product->getSku()];
         $productGrid->open()->getProductGrid()->searchAndOpen($filter);
 
-        $fixtureData = $productPage->getForm()->getData($product);
-        $formData = $this->prepareFixtureData($product);
+        $formData = $productPage->getForm()->getData($product);
+        $fixtureData = $this->prepareFixtureData($product);
 
         $errors = $this->compareArray($fixtureData, $formData);
         \PHPUnit_Framework_Assert::assertTrue(
@@ -129,7 +129,7 @@ class AssertProductForm extends AbstractConstraint
     protected function compareArray(array $fixtureData, array $formData)
     {
         $errors = [];
-        $keysDiff = array_diff(array_keys($fixtureData), array_keys($formData));
+        $keysDiff = array_diff(array_keys($formData), array_keys($fixtureData));
         if (!empty($keysDiff)) {
             return ['- fixture data do not correspond to form data in composition.'];
         }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductInCategory.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductInCategory.php
index 5dd30e4ca1c..58c7fd8faed 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductInCategory.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductInCategory.php
@@ -27,7 +27,7 @@ namespace Magento\Catalog\Test\Constraint;
 use Mtf\Fixture\FixtureInterface;
 use Magento\Cms\Test\Page\CmsIndex;
 use Mtf\Constraint\AbstractConstraint;
-use Magento\Catalog\Test\Fixture\CatalogCategoryEntity;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
 
 /**
@@ -48,14 +48,14 @@ class AssertProductInCategory extends AbstractConstraint
      * @param CatalogCategoryView $catalogCategoryView
      * @param CmsIndex $cmsIndex
      * @param FixtureInterface $product
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @return void
      */
     public function processAssert(
         CatalogCategoryView $catalogCategoryView,
         CmsIndex $cmsIndex,
         FixtureInterface $product,
-        CatalogCategoryEntity $category
+        CatalogCategory $category
     ) {
         // Open category view page and check visible product
         $cmsIndex->open();
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductIsNotDisplayingOnFrontend.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductIsNotDisplayingOnFrontend.php
index 5efd08e691e..c5060570866 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductIsNotDisplayingOnFrontend.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductIsNotDisplayingOnFrontend.php
@@ -27,7 +27,7 @@ namespace Magento\Catalog\Test\Constraint;
 use Mtf\Fixture\FixtureInterface;
 use Magento\Cms\Test\Page\CmsIndex;
 use Mtf\Constraint\AbstractConstraint;
-use Magento\Catalog\Test\Fixture\CatalogCategoryEntity;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 use Magento\CatalogSearch\Test\Page\CatalogsearchResult;
 use Magento\Catalog\Test\Page\Product\CatalogProductView;
 use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
@@ -57,7 +57,7 @@ class AssertProductIsNotDisplayingOnFrontend extends AbstractConstraint
      * @param CatalogCategoryView $catalogCategoryView
      * @param CmsIndex $cmsIndex
      * @param FixtureInterface $product
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      */
     public function processAssert(
         CatalogProductView $catalogProductView,
@@ -65,7 +65,7 @@ class AssertProductIsNotDisplayingOnFrontend extends AbstractConstraint
         CatalogCategoryView $catalogCategoryView,
         CmsIndex $cmsIndex,
         FixtureInterface $product,
-        CatalogCategoryEntity $category
+        CatalogCategory $category
     ) {
         $errors = [];
         // Check the product page is not available
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductVisibleInCategory.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductVisibleInCategory.php
index 36268f5db5f..09e782d177d 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductVisibleInCategory.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertProductVisibleInCategory.php
@@ -27,7 +27,7 @@ namespace Magento\Catalog\Test\Constraint;
 use Mtf\Fixture\FixtureInterface;
 use Magento\Cms\Test\Page\CmsIndex;
 use Mtf\Constraint\AbstractConstraint;
-use Magento\Catalog\Test\Fixture\CatalogCategoryEntity;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
 
 /**
@@ -63,14 +63,14 @@ class AssertProductVisibleInCategory extends AbstractConstraint
      * @param CatalogCategoryView $catalogCategoryView
      * @param CmsIndex $cmsIndex
      * @param FixtureInterface $product
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @return void
      */
     public function processAssert(
         CatalogCategoryView $catalogCategoryView,
         CmsIndex $cmsIndex,
         FixtureInterface $product,
-        CatalogCategoryEntity $category
+        CatalogCategory $category
     ) {
         $cmsIndex->open();
         $cmsIndex->getTopmenu()->selectCategoryByName($category->getName());
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertRelatedProductsSection.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertRelatedProductsSection.php
new file mode 100644
index 00000000000..99cb9c60ebb
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertRelatedProductsSection.php
@@ -0,0 +1,82 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Cms\Test\Page\CmsIndex;
+use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
+use Magento\Catalog\Test\Page\Product\CatalogProductView;
+
+/**
+ * Class AssertRelatedProductsSection
+ */
+class AssertRelatedProductsSection extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'middle';
+
+    /**
+     * Assert that product is displayed in related products section
+     *
+     * @param CatalogProductSimple $product1
+     * @param CatalogProductSimple $product2
+     * @param CmsIndex $cmsIndex
+     * @param CatalogCategoryView $catalogCategoryView
+     * @param CatalogProductView $catalogProductView
+     * @return void
+     */
+    public function processAssert(
+        CatalogProductSimple $product1,
+        CatalogProductSimple $product2,
+        CmsIndex $cmsIndex,
+        CatalogCategoryView $catalogCategoryView,
+        CatalogProductView $catalogProductView
+    ) {
+        $categoryName = $product1->getCategoryIds()[0]['name'];
+        $cmsIndex->open();
+        $cmsIndex->getTopmenu()->selectCategoryByName($categoryName);
+        $catalogCategoryView->getListProductBlock()->openProductViewPage($product1->getName());
+
+        \PHPUnit_Framework_Assert::assertTrue(
+            $catalogProductView->getRelatedProductBlock()->isRelatedProductVisible($product2->getName()),
+            'Product \'' . $product2->getName() . '\' is absent in related products.'
+        );
+    }
+
+    /**
+     * Text success product is displayed in related products section
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Product is displayed in related products section.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertUpSellsProductsSection.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertUpSellsProductsSection.php
new file mode 100644
index 00000000000..9a90a23493e
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Constraint/AssertUpSellsProductsSection.php
@@ -0,0 +1,82 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Cms\Test\Page\CmsIndex;
+use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
+use Magento\Catalog\Test\Page\Product\CatalogProductView;
+
+/**
+ * Class AssertUpSellsProductsSection
+ */
+class AssertUpSellsProductsSection extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'middle';
+
+    /**
+     * Assert that product is displayed in up-sell section
+     *
+     * @param CatalogProductSimple $product1
+     * @param CatalogProductSimple $product2
+     * @param CmsIndex $cmsIndex
+     * @param CatalogCategoryView $catalogCategoryView
+     * @param CatalogProductView $catalogProductView
+     * @return void
+     */
+    public function processAssert(
+        CatalogProductSimple $product1,
+        CatalogProductSimple $product2,
+        CmsIndex $cmsIndex,
+        CatalogCategoryView $catalogCategoryView,
+        CatalogProductView $catalogProductView
+    ) {
+        $categoryName = $product1->getCategoryIds()[0]['name'];
+        $cmsIndex->open();
+        $cmsIndex->getTopmenu()->selectCategoryByName($categoryName);
+        $catalogCategoryView->getListProductBlock()->openProductViewPage($product1->getName());
+
+        \PHPUnit_Framework_Assert::assertTrue(
+            $catalogProductView->getUpsellBlock()->isUpsellProductVisible($product2->getName()),
+            'Product \'' . $product2->getName() . '\' is absent in up-sells products.'
+        );
+    }
+
+    /**
+     * Text success product is displayed in up-sell section
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Product is displayed in up-sell section.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategoryEntity.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategory.php
similarity index 70%
rename from dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategoryEntity.php
rename to dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategory.php
index 395510caa90..f9af209aced 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategoryEntity.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategory.php
@@ -27,20 +27,20 @@ namespace Magento\Catalog\Test\Fixture;
 use Mtf\Fixture\InjectableFixture;
 
 /**
- * Class CatalogCategoryEntity
+ * Class CatalogCategory
  * Category fixture
  */
-class CatalogCategoryEntity extends InjectableFixture
+class CatalogCategory extends InjectableFixture
 {
     /**
      * @var string
      */
-    protected $repositoryClass = 'Magento\Catalog\Test\Repository\CatalogCategoryEntity';
+    protected $repositoryClass = 'Magento\Catalog\Test\Repository\CatalogCategory';
 
     /**
      * @var string
      */
-    protected $handlerInterface = 'Magento\Catalog\Test\Handler\CatalogCategoryEntity\CatalogCategoryEntityInterface';
+    protected $handlerInterface = 'Magento\Catalog\Test\Handler\CatalogCategory\CatalogCategoryInterface';
 
     protected $defaultDataSet = [
         'name' => 'Category%isolation%',
@@ -75,6 +75,14 @@ class CatalogCategoryEntity extends InjectableFixture
         'input' => '',
     ];
 
+    protected $description = [
+        'attribute_code' => 'description',
+        'backend_type' => 'text',
+        'is_required' => '0',
+        'default_value' => '',
+        'input' => 'textarea',
+    ];
+
     protected $parent_id = [
         'attribute_code' => 'parent_id',
         'backend_type' => 'int',
@@ -131,6 +139,50 @@ class CatalogCategoryEntity extends InjectableFixture
         'input' => '',
     ];
 
+    protected $available_product_listing_config = [
+        'attribute_code' => 'available_product_listing_config',
+        'backend_type' => 'int',
+        'is_required' => '',
+        'default_value' => '',
+        'group' => 'display_setting',
+        'input' => 'checkbox',
+    ];
+
+    protected $available_sort_by = [
+        'attribute_code' => 'available_sort_by',
+        'backend_type' => 'varchar',
+        'is_required' => '0',
+        'default_value' => '',
+        'group' => 'display_setting',
+        'input' => 'multiselect',
+    ];
+
+    protected $default_product_listing_config = [
+        'attribute_code' => 'default_product_listing_config',
+        'backend_type' => 'varchar',
+        'is_required' => '0',
+        'default_value' => '',
+        'group' => 'display_setting',
+        'input' => 'checkbox',
+    ];
+
+    protected $default_sort_by = [
+        'attribute_code' => 'default_sort_by',
+        'backend_type' => 'varchar',
+        'is_required' => '0',
+        'default_value' => '',
+        'group' => 'display_setting',
+        'input' => 'select',
+    ];
+
+    protected $meta_title = [
+        'attribute_code' => 'meta_title',
+        'backend_type' => 'text',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+    ];
+
     protected $id = [
         'attribute_code' => 'id',
         'backend_type' => 'virtual',
@@ -171,6 +223,11 @@ class CatalogCategoryEntity extends InjectableFixture
         return $this->getData('attribute_set_id');
     }
 
+    public function getDescription()
+    {
+        return $this->getData('description');
+    }
+
     public function getParentId()
     {
         return $this->getData('parent_id');
@@ -206,6 +263,31 @@ class CatalogCategoryEntity extends InjectableFixture
         return $this->getData('children_count');
     }
 
+    public function getAvailableProductListingConfig()
+    {
+        return $this->getData('available_product_listing_config');
+    }
+
+    public function getAvailableSortBy()
+    {
+        return $this->getData('available_sort_by');
+    }
+
+    public function getDefaultProductListingConfig()
+    {
+        return $this->getData('default_product_listing_config');
+    }
+
+    public function getDefaultSortBy()
+    {
+        return $this->getData('default_sort_by');
+    }
+
+    public function getMetaTitle()
+    {
+        return $this->getData('meta_title');
+    }
+
     public function getId()
     {
         return $this->getData('id');
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategoryEntity.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategory.xml
similarity index 70%
rename from dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategoryEntity.xml
rename to dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategory.xml
index cc8301ed27d..f491f2349f7 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategoryEntity.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogCategory.xml
@@ -23,9 +23,9 @@
  * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
  */
 -->
-<fixture class="Magento\Catalog\Test\Fixture\CatalogCategoryEntity">
+<fixture class="Magento\Catalog\Test\Fixture\CatalogCategory">
     <module>Magento_Catalog</module>
-    <type>flat</type>
+    <type>eav</type>
     <entity_type>catalog_category_entity</entity_type>
     <collection>Magento\Catalog\Model\Resource\Category\Collection</collection>
     <fields>
@@ -50,6 +50,13 @@
             <default_value>0</default_value>
             <input></input>
         </attribute_set_id>
+        <description>
+            <attribute_code>description</attribute_code>
+            <backend_type>text</backend_type>
+            <is_required>0</is_required>
+            <default_value></default_value>
+            <input>textarea</input>
+        </description>
         <parent_id>
             <attribute_code>parent_id</attribute_code>
             <backend_type>int</backend_type>
@@ -99,6 +106,41 @@
             <default_value></default_value>
             <input></input>
         </children_count>
+        <available_product_listing_config>
+            <attribute_code>available_product_listing_config</attribute_code>
+            <backend_type>int</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input>checkbox</input>
+        </available_product_listing_config>
+        <available_sort_by>
+            <attribute_code>available_sort_by</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required>0</is_required>
+            <default_value></default_value>
+            <input>multiselect</input>
+        </available_sort_by>
+        <default_product_listing_config>
+            <attribute_code>default_product_listing_config</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required>0</is_required>
+            <default_value></default_value>
+            <input>checkbox</input>
+        </default_product_listing_config>
+        <default_sort_by>
+            <attribute_code>default_sort_by</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required>0</is_required>
+            <default_value></default_value>
+            <input>select</input>
+        </default_sort_by>
+        <meta_title>
+            <attribute_code>meta_title</attribute_code>
+            <backend_type>text</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </meta_title>
         <id>
             <attribute_code>id</attribute_code>
             <backend_type>virtual</backend_type>
@@ -120,6 +162,6 @@
             <backend_type>virtual</backend_type>
         </include_in_menu>
     </fields>
-    <repository_class>Magento\Catalog\Test\Repository\CatalogCategoryEntity</repository_class>
-    <handler_interface>Magento\Catalog\Test\Handler\CatalogCategoryEntity\CatalogCategoryEntityInterface</handler_interface>
+    <repository_class>Magento\Catalog\Test\Repository\CatalogCategory</repository_class>
+    <handler_interface>Magento\Catalog\Test\Handler\CatalogCategory\CatalogCategoryInterface</handler_interface>
 </fixture>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute.php
new file mode 100644
index 00000000000..246c8d68b02
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute.php
@@ -0,0 +1,559 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Fixture;
+
+use Mtf\Fixture\InjectableFixture;
+
+/**
+ * Class CatalogAttributeEntity
+ */
+class CatalogProductAttribute extends InjectableFixture
+{
+    /**
+     * @var string
+     */
+    protected $repositoryClass = 'Magento\Catalog\Test\Repository\CatalogAttributeEntity';
+
+    /**
+     * @var string
+     */
+    protected $handlerInterface = 'Magento\Catalog\Test\Handler\CatalogAttributeEntity\CatalogAttributeEntityInterface';
+
+    protected $defaultDataSet = [
+        'frontend_label' => 'attribute_label%isolation%',
+        'frontend_input' => 'Text Field',
+        'is_required' => 'No'
+    ];
+
+    protected $attribute_id = [
+        'attribute_code' => 'attribute_id',
+        'backend_type' => 'smallint',
+        'is_required' => '1',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $entity_type_id = [
+        'attribute_code' => 'entity_type_id',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+    ];
+
+    protected $attribute_code = [
+        'attribute_code' => 'attribute_code',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+        'group' => 'advanced-properties',
+    ];
+
+    protected $attribute_model = [
+        'attribute_code' => 'attribute_model',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $backend_model = [
+        'attribute_code' => 'backend_model',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $backend_type = [
+        'attribute_code' => 'backend_type',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => 'static',
+        'input' => '',
+    ];
+
+    protected $backend_table = [
+        'attribute_code' => 'backend_table',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $frontend_model = [
+        'attribute_code' => 'frontend_model',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $frontend_input = [
+        'attribute_code' => 'frontend_input',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => 'select',
+        'group' => 'properties',
+    ];
+
+    protected $frontend_label = [
+        'attribute_code' => 'frontend_label',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+        'group' => 'properties',
+    ];
+
+    protected $manage_frontend_label = [
+        'attribute_code' => 'manage_frontend_label',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+        'group' => 'manage-labels',
+    ];
+
+    protected $frontend_class = [
+        'attribute_code' => 'frontend_class',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $source_model = [
+        'attribute_code' => 'source_model',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $is_required = [
+        'attribute_code' => 'is_required',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => 'select',
+        'group' => 'properties',
+    ];
+
+    protected $is_user_defined = [
+        'attribute_code' => 'is_user_defined',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+    ];
+
+    protected $default_value = [
+        'attribute_code' => 'default_value',
+        'backend_type' => 'text',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+        'group' => 'advanced-properties',
+    ];
+
+    protected $is_unique = [
+        'attribute_code' => 'is_unique',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'advanced-properties',
+    ];
+
+    protected $note = [
+        'attribute_code' => 'note',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $frontend_input_renderer = [
+        'attribute_code' => 'frontend_input_renderer',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $is_global = [
+        'attribute_code' => 'is_global',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '1',
+        'input' => '',
+        'group' => 'advanced-properties',
+    ];
+
+    protected $is_visible = [
+        'attribute_code' => 'is_visible',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '1',
+        'input' => '',
+    ];
+
+    protected $is_searchable = [
+        'attribute_code' => 'is_searchable',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'frontend-properties',
+    ];
+
+    protected $is_filterable = [
+        'attribute_code' => 'is_filterable',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'frontend-properties',
+    ];
+
+    protected $is_comparable = [
+        'attribute_code' => 'is_comparable',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'frontend-properties',
+    ];
+
+    protected $is_visible_on_front = [
+        'attribute_code' => 'is_visible_on_front',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'frontend-properties',
+    ];
+
+    protected $is_html_allowed_on_front = [
+        'attribute_code' => 'is_html_allowed_on_front',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'frontend-properties',
+    ];
+
+    protected $is_used_for_price_rules = [
+        'attribute_code' => 'is_used_for_price_rules',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'frontend-properties',
+    ];
+
+    protected $is_filterable_in_search = [
+        'attribute_code' => 'is_filterable_in_search',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'frontend-properties',
+    ];
+
+    protected $used_in_product_listing = [
+        'attribute_code' => 'used_in_product_listing',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'frontend-properties',
+    ];
+
+    protected $used_for_sort_by = [
+        'attribute_code' => 'used_for_sort_by',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'frontend-properties',
+    ];
+
+    protected $apply_to = [
+        'attribute_code' => 'apply_to',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $is_visible_in_advanced_search = [
+        'attribute_code' => 'is_visible_in_advanced_search',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'frontend-properties',
+    ];
+
+    protected $position = [
+        'attribute_code' => 'position',
+        'backend_type' => 'int',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+    ];
+
+    protected $is_wysiwyg_enabled = [
+        'attribute_code' => 'is_wysiwyg_enabled',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+    ];
+
+    protected $is_used_for_promo_rules = [
+        'attribute_code' => 'is_used_for_promo_rules',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+    ];
+
+    protected $is_configurable = [
+        'attribute_code' => 'is_configurable',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+        'group' => 'advanced-properties',
+    ];
+
+    protected $search_weight = [
+        'attribute_code' => 'search_weight',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '1',
+        'input' => '',
+    ];
+
+    protected $options = [
+        'attribute_code' => 'options',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+        'source' => '\Magento\Catalog\Test\Fixture\CatalogProductAttribute\Options',
+        'group' => 'manage-options'
+    ];
+
+    public function getAttributeId()
+    {
+        return $this->getData('attribute_id');
+    }
+
+    public function getEntityTypeId()
+    {
+        return $this->getData('entity_type_id');
+    }
+
+    public function getAttributeCode()
+    {
+        return $this->getData('attribute_code');
+    }
+
+    public function getAttributeModel()
+    {
+        return $this->getData('attribute_model');
+    }
+
+    public function getBackendModel()
+    {
+        return $this->getData('backend_model');
+    }
+
+    public function getBackendType()
+    {
+        return $this->getData('backend_type');
+    }
+
+    public function getBackendTable()
+    {
+        return $this->getData('backend_table');
+    }
+
+    public function getFrontendModel()
+    {
+        return $this->getData('frontend_model');
+    }
+
+    public function getFrontendInput()
+    {
+        return $this->getData('frontend_input');
+    }
+
+    public function getFrontendLabel()
+    {
+        return $this->getData('frontend_label');
+    }
+
+    public function getManageFrontendLabel()
+    {
+        return $this->getData('manage_frontend_label');
+    }
+
+    public function getFrontendClass()
+    {
+        return $this->getData('frontend_class');
+    }
+
+    public function getSourceModel()
+    {
+        return $this->getData('source_model');
+    }
+
+    public function getIsRequired()
+    {
+        return $this->getData('is_required');
+    }
+
+    public function getIsUserDefined()
+    {
+        return $this->getData('is_user_defined');
+    }
+
+    public function getDefaultValue()
+    {
+        return $this->getData('default_value');
+    }
+
+    public function getIsUnique()
+    {
+        return $this->getData('is_unique');
+    }
+
+    public function getNote()
+    {
+        return $this->getData('note');
+    }
+
+    public function getFrontendInputRenderer()
+    {
+        return $this->getData('frontend_input_renderer');
+    }
+
+    public function getIsGlobal()
+    {
+        return $this->getData('is_global');
+    }
+
+    public function getIsVisible()
+    {
+        return $this->getData('is_visible');
+    }
+
+    public function getIsSearchable()
+    {
+        return $this->getData('is_searchable');
+    }
+
+    public function getIsFilterable()
+    {
+        return $this->getData('is_filterable');
+    }
+
+    public function getIsComparable()
+    {
+        return $this->getData('is_comparable');
+    }
+
+    public function getIsVisibleOnFront()
+    {
+        return $this->getData('is_visible_on_front');
+    }
+
+    public function getIsHtmlAllowedOnFront()
+    {
+        return $this->getData('is_html_allowed_on_front');
+    }
+
+    public function getIsUsedForPriceRules()
+    {
+        return $this->getData('is_used_for_price_rules');
+    }
+
+    public function getIsFilterableInSearch()
+    {
+        return $this->getData('is_filterable_in_search');
+    }
+
+    public function getUsedInProductListing()
+    {
+        return $this->getData('used_in_product_listing');
+    }
+
+    public function getUsedForSortBy()
+    {
+        return $this->getData('used_for_sort_by');
+    }
+
+    public function getApplyTo()
+    {
+        return $this->getData('apply_to');
+    }
+
+    public function getIsVisibleInAdvancedSearch()
+    {
+        return $this->getData('is_visible_in_advanced_search');
+    }
+
+    public function getPosition()
+    {
+        return $this->getData('position');
+    }
+
+    public function getIsWysiwygEnabled()
+    {
+        return $this->getData('is_wysiwyg_enabled');
+    }
+
+    public function getIsUsedForPromoRules()
+    {
+        return $this->getData('is_used_for_promo_rules');
+    }
+
+    public function getIsConfigurable()
+    {
+        return $this->getData('is_configurable');
+    }
+
+    public function getSearchWeight()
+    {
+        return $this->getData('search_weight');
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute.xml
new file mode 100644
index 00000000000..ec83b427149
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute.xml
@@ -0,0 +1,293 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<fixture class="Magento\Catalog\Test\Fixture\CatalogProductAttribute">
+    <module>Magento_Catalog</module>
+    <type>composite</type>
+    <entities>
+        <eav_attribute>eav_attribute</eav_attribute>
+        <catalog_eav_attribute>catalog_eav_attribute</catalog_eav_attribute>
+    </entities>
+    <collection>Magento\Catalog\Model\Resource\Attribute</collection>
+    <fields>
+        <attribute_id>
+            <attribute_code>attribute_id</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required>1</is_required>
+            <default_value></default_value>
+            <input></input>
+        </attribute_id>
+        <entity_type_id>
+            <attribute_code>entity_type_id</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </entity_type_id>
+        <attribute_code>
+            <attribute_code>attribute_code</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </attribute_code>
+        <attribute_model>
+            <attribute_code>attribute_model</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </attribute_model>
+        <backend_model>
+            <attribute_code>backend_model</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </backend_model>
+        <backend_type>
+            <attribute_code>backend_type</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value>static</default_value>
+            <input></input>
+        </backend_type>
+        <backend_table>
+            <attribute_code>backend_table</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </backend_table>
+        <frontend_model>
+            <attribute_code>frontend_model</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </frontend_model>
+        <frontend_input>
+            <attribute_code>frontend_input</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+            <group>properties</group>
+        </frontend_input>
+        <frontend_label>
+            <attribute_code>frontend_label</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+            <group>properties</group>
+        </frontend_label>
+        <frontend_class>
+            <attribute_code>frontend_class</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </frontend_class>
+        <source_model>
+            <attribute_code>source_model</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </source_model>
+        <is_required>
+            <attribute_code>is_required</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+            <group>properties</group>
+        </is_required>
+        <is_user_defined>
+            <attribute_code>is_user_defined</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_user_defined>
+        <default_value>
+            <attribute_code>default_value</attribute_code>
+            <backend_type>text</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </default_value>
+        <is_unique>
+            <attribute_code>is_unique</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_unique>
+        <note>
+            <attribute_code>note</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </note>
+        <frontend_input_renderer>
+            <attribute_code>frontend_input_renderer</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </frontend_input_renderer>
+        <is_global>
+            <attribute_code>is_global</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>1</default_value>
+            <input></input>
+        </is_global>
+        <is_visible>
+            <attribute_code>is_visible</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>1</default_value>
+            <input></input>
+        </is_visible>
+        <is_searchable>
+            <attribute_code>is_searchable</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_searchable>
+        <is_filterable>
+            <attribute_code>is_filterable</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_filterable>
+        <is_comparable>
+            <attribute_code>is_comparable</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_comparable>
+        <is_visible_on_front>
+            <attribute_code>is_visible_on_front</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_visible_on_front>
+        <is_html_allowed_on_front>
+            <attribute_code>is_html_allowed_on_front</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_html_allowed_on_front>
+        <is_used_for_price_rules>
+            <attribute_code>is_used_for_price_rules</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_used_for_price_rules>
+        <is_filterable_in_search>
+            <attribute_code>is_filterable_in_search</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_filterable_in_search>
+        <used_in_product_listing>
+            <attribute_code>used_in_product_listing</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </used_in_product_listing>
+        <used_for_sort_by>
+            <attribute_code>used_for_sort_by</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </used_for_sort_by>
+        <apply_to>
+            <attribute_code>apply_to</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </apply_to>
+        <is_visible_in_advanced_search>
+            <attribute_code>is_visible_in_advanced_search</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_visible_in_advanced_search>
+        <position>
+            <attribute_code>position</attribute_code>
+            <backend_type>int</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </position>
+        <is_wysiwyg_enabled>
+            <attribute_code>is_wysiwyg_enabled</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_wysiwyg_enabled>
+        <is_used_for_promo_rules>
+            <attribute_code>is_used_for_promo_rules</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </is_used_for_promo_rules>
+        <is_configurable>
+            <attribute_code>is_configurable</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+        </is_configurable>
+        <search_weight>
+            <attribute_code>search_weight</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>1</default_value>
+            <input></input>
+        </search_weight>
+    </fields>
+    <repository_class>Magento\Catalog\Test\Repository\CatalogAttributeEntity</repository_class>
+    <handler_interface>Magento\Catalog\Test\Handler\CatalogAttributeEntity\CatalogAttributeEntityInterface</handler_interface>
+</fixture>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute/Options.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute/Options.php
new file mode 100644
index 00000000000..b87fdb5c5c9
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductAttribute/Options.php
@@ -0,0 +1,101 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Fixture\CatalogProductAttribute;
+
+use Mtf\Fixture\FixtureInterface;
+
+/**
+ * Class Options
+ * Prepare Manage Options for attribute
+ */
+class Options implements FixtureInterface
+{
+    /**
+     * @constructor
+     * @param array $params
+     * @param array $data
+     */
+    public function __construct(array $params, array $data = [])
+    {
+        $this->params = $params;
+        if (isset($data['preset'])) {
+            $this->data = $this->getPreset($data['preset']);
+        }
+    }
+
+    /**
+     * Persist attribute options
+     *
+     * @return void
+     */
+    public function persist()
+    {
+        //
+    }
+
+    /**
+     * Return prepared data set
+     *
+     * @param string|null $key
+     * @return mixed
+     */
+    public function getData($key = null)
+    {
+        return $this->data;
+    }
+
+    /**
+     * Return data set configuration settings
+     *
+     * @return array
+     */
+    public function getDataConfig()
+    {
+        return $this->params;
+    }
+
+    /**
+     * Preset for Attribute manage options
+     *
+     * @param string $name
+     * @return array|null
+     */
+    protected function getPreset($name)
+    {
+        $presets = [
+            'default' => [
+                [
+                    'is_default' => 'Yes',
+                    'admin' => 'Admin',
+                    'view' => 'Electronics',
+                ]
+            ],
+        ];
+        if (!isset($presets[$name])) {
+            return null;
+        }
+        return $presets[$name];
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple.php
index e4422708a4e..117ebb65743 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple.php
@@ -29,6 +29,7 @@ use Mtf\Handler\HandlerFactory;
 use Mtf\Fixture\FixtureFactory;
 use Mtf\Fixture\InjectableFixture;
 use Mtf\Repository\RepositoryFactory;
+use Mtf\System\Event\EventManagerInterface;
 
 /**
  * Class CatalogProductSimple
@@ -54,6 +55,7 @@ class CatalogProductSimple extends InjectableFixture
      * @param RepositoryFactory $repositoryFactory
      * @param FixtureFactory $fixtureFactory
      * @param HandlerFactory $handlerFactory
+     * @param EventManagerInterface $eventManager
      * @param array $data
      * @param string $dataSet
      * @param bool $persist
@@ -63,6 +65,7 @@ class CatalogProductSimple extends InjectableFixture
         RepositoryFactory $repositoryFactory,
         FixtureFactory $fixtureFactory,
         HandlerFactory $handlerFactory,
+        EventManagerInterface $eventManager,
         array $data = [],
         $dataSet = '',
         $persist = false
@@ -72,6 +75,7 @@ class CatalogProductSimple extends InjectableFixture
             $repositoryFactory,
             $fixtureFactory,
             $handlerFactory,
+            $eventManager,
             $data,
             $dataSet,
             $persist
@@ -465,6 +469,7 @@ class CatalogProductSimple extends InjectableFixture
         'default_value' => 'Taxable Goods',
         'input' => 'select',
         'group' => 'product-details',
+        'source' => 'Magento\Catalog\Test\Fixture\CatalogProductSimple\TaxClass',
     ];
 
     protected $thumbnail = [
@@ -507,6 +512,7 @@ class CatalogProductSimple extends InjectableFixture
         'is_required' => '0',
         'default_value' => '',
         'input' => 'text',
+        'group' => 'autosettings',
     ];
 
     protected $url_path = [
@@ -564,6 +570,12 @@ class CatalogProductSimple extends InjectableFixture
         'source' => 'Magento\Catalog\Test\Fixture\CatalogProductSimple\CustomOptions',
     ];
 
+    protected $website_ids = [
+        'attribute_code' => 'website_ids',
+        'backend_type' => 'virtual',
+        'default_value' => 'Main Website',
+    ];
+
     public function getCategoryIds()
     {
         return $this->getData('category_ids');
@@ -848,4 +860,9 @@ class CatalogProductSimple extends InjectableFixture
     {
         return $this->getData('custom_options');
     }
+
+    public function getWebsiteIds()
+    {
+        return $this->getData('website_ids');
+    }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple.xml
index eeb11a33503..703252c0d22 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple.xml
@@ -391,6 +391,7 @@
             <is_required>0</is_required>
             <default_value></default_value>
             <input>text</input>
+            <group>autosettings</group>
         </url_key>
         <url_path>
             <attribute_code>url_path</attribute_code>
@@ -440,6 +441,11 @@
             <group>customer-options</group>
             <fixture>Magento\Catalog\Test\Fixture\CatalogProductSimple\CustomOptions</fixture>
         </custom_options>
+        <website_ids>
+            <attribute_code>website_ids</attribute_code>
+            <backend_type>virtual</backend_type>
+            <default_value>Main Website</default_value>
+        </website_ids>
     </fields>
     <data_set>
         <sku></sku>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/CategoryIds.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/CategoryIds.php
index 1cd466a917e..be1ec366fad 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/CategoryIds.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/CategoryIds.php
@@ -24,7 +24,7 @@
 
 namespace Magento\Catalog\Test\Fixture\CatalogProductSimple;
 
-use Magento\Catalog\Test\Fixture\CatalogCategoryEntity;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 use Mtf\Fixture\FixtureFactory;
 use Mtf\Fixture\FixtureInterface;
 
@@ -62,9 +62,9 @@ class CategoryIds implements FixtureInterface
 
         if (!empty($data['category'])
             && empty($data['presets'])
-            && $data['category'] instanceof CatalogCategoryEntity
+            && $data['category'] instanceof CatalogCategory
         ) {
-            /** @var CatalogCategoryEntity $category */
+            /** @var CatalogCategory $category */
             $category = $data['category'];
             $this->data[] = [
                 'id' => $category->getId(),
@@ -72,12 +72,13 @@ class CategoryIds implements FixtureInterface
             ];
             $this->category[] = $category;
         } elseif (isset($data['presets']) && $data['presets'] !== '-') {
+
             $presets = explode(',', $data['presets']);
             foreach ($presets as $preset) {
-                $category = $fixtureFactory->createByCode('catalogCategoryEntity', ['dataSet' => $preset]);
+                $category = $fixtureFactory->createByCode('catalogCategory', ['dataSet' => $preset]);
                 $category->persist();
 
-                /** @var CatalogCategoryEntity $category */
+                /** @var CatalogCategory $category */
                 $this->data[] = [
                     'id' => $category->getId(),
                     'name' => $category->getName(),
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/Price.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/Price.php
index 4f278004a67..a8726289546 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/Price.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/Price.php
@@ -24,7 +24,6 @@
 
 namespace Magento\Catalog\Test\Fixture\CatalogProductSimple;
 
-use Mtf\Fixture\FixtureFactory;
 use Mtf\Fixture\FixtureInterface;
 
 /**
@@ -56,6 +55,14 @@ class Price implements FixtureInterface
         $this->params = $params;
         if (isset($data['value'])) {
             $this->data = $data['value'];
+            if (is_array($this->data)) {
+                $this->data = array_filter(
+                    $this->data,
+                    function ($value) {
+                        return $value !== '-';
+                    }
+                );
+            }
         }
         if (isset($data['preset'])) {
             $this->currentPreset = $data['preset'];
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/TaxClass.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/TaxClass.php
new file mode 100644
index 00000000000..2e6869e5425
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductSimple/TaxClass.php
@@ -0,0 +1,116 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Fixture\CatalogProductSimple;
+
+use Mtf\Fixture\FixtureFactory;
+use Mtf\Fixture\FixtureInterface;
+
+/**
+ * Class TaxClass
+ *
+ * Data keys:
+ *  - dataSet
+ *  - tax_product_class
+ */
+class TaxClass implements FixtureInterface
+{
+    /**
+     * Tax class name
+     *
+     * @var string
+     */
+    protected $data;
+
+    /**
+     * Tax class fixture
+     *
+     * @var \Magento\Tax\Test\Fixture\TaxClass
+     */
+    protected $taxClass;
+
+    /**
+     * @param FixtureFactory $fixtureFactory
+     * @param array $params
+     * @param array $data
+     */
+    public function __construct(FixtureFactory $fixtureFactory, array $params, array $data = [])
+    {
+        $this->params = $params;
+        /** @var \Magento\Tax\Test\Fixture\TaxClass $taxClass */
+        if (isset($data['dataSet']) && $data['dataSet'] !== '-') {
+            $taxClass = $fixtureFactory->createByCode('taxClass', ['dataSet' => $data['dataSet']]);
+            $this->taxClass = $taxClass;
+            $this->data = $taxClass->getClassName();
+        }
+        if (isset($data['tax_product_class'])
+            && $data['tax_product_class'] instanceof \Magento\Tax\Test\Fixture\TaxClass
+        ) {
+            $taxClass = $data['tax_product_class'];
+            $this->taxClass = $taxClass;
+            $this->data = $taxClass->getClassName();
+        }
+    }
+
+    /**
+     * Persist custom selections tax classes
+     *
+     * @return void
+     */
+    public function persist()
+    {
+        //
+    }
+
+    /**
+     * Return prepared data set
+     *
+     * @param string|null $key
+     * @return mixed
+     */
+    public function getData($key = null)
+    {
+        return $this->data;
+    }
+
+    /**
+     * Return data set configuration settings
+     *
+     * @return string
+     */
+    public function getDataConfig()
+    {
+        return $this->params;
+    }
+
+    /**
+     * Return tax class fixture
+     *
+     * @return \Magento\Tax\Test\Fixture\TaxClass
+     */
+    public function getTaxClass()
+    {
+        return $this->taxClass;
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductVirtual.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductVirtual.php
index 2f6edb73096..71f159d6ea1 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductVirtual.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductVirtual.php
@@ -29,6 +29,7 @@ use Mtf\Handler\HandlerFactory;
 use Mtf\Fixture\FixtureFactory;
 use Mtf\Fixture\InjectableFixture;
 use Mtf\Repository\RepositoryFactory;
+use Mtf\System\Event\EventManagerInterface;
 
 /**
  * Class CatalogProductVirtual
@@ -53,6 +54,7 @@ class CatalogProductVirtual extends InjectableFixture
      * @param RepositoryFactory $repositoryFactory
      * @param FixtureFactory $fixtureFactory
      * @param HandlerFactory $handlerFactory
+     * @param EventManagerInterface $eventManager
      * @param array $data
      * @param string $dataSet
      * @param bool $persist
@@ -62,6 +64,7 @@ class CatalogProductVirtual extends InjectableFixture
         RepositoryFactory $repositoryFactory,
         FixtureFactory $fixtureFactory,
         HandlerFactory $handlerFactory,
+        EventManagerInterface $eventManager,
         array $data = [],
         $dataSet = '',
         $persist = false
@@ -71,6 +74,7 @@ class CatalogProductVirtual extends InjectableFixture
             $repositoryFactory,
             $fixtureFactory,
             $handlerFactory,
+            $eventManager,
             $data,
             $dataSet,
             $persist
@@ -462,6 +466,7 @@ class CatalogProductVirtual extends InjectableFixture
         'default_value' => 'Taxable Goods',
         'input' => 'select',
         'group' => 'product-details',
+        'source' => 'Magento\Catalog\Test\Fixture\CatalogProductSimple\TaxClass',
     ];
 
     protected $thumbnail = [
@@ -504,6 +509,7 @@ class CatalogProductVirtual extends InjectableFixture
         'is_required' => '0',
         'default_value' => '',
         'input' => 'text',
+        'group' => 'autosettings',
     ];
 
     protected $url_path = [
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductVirtual.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductVirtual.xml
index 80a1d596ef4..69fd4f87cc8 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductVirtual.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Fixture/CatalogProductVirtual.xml
@@ -391,6 +391,7 @@
             <is_required>0</is_required>
             <default_value></default_value>
             <input>text</input>
+            <group>autosettings</group>
         </url_key>
         <url_path>
             <attribute_code>url_path</attribute_code>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategoryEntity/CatalogCategoryEntityInterface.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategory/CatalogCategoryInterface.php
similarity index 84%
rename from dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategoryEntity/CatalogCategoryEntityInterface.php
rename to dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategory/CatalogCategoryInterface.php
index 27feac56803..00ae6419639 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategoryEntity/CatalogCategoryEntityInterface.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategory/CatalogCategoryInterface.php
@@ -22,14 +22,14 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-namespace Magento\Catalog\Test\Handler\CatalogCategoryEntity;
+namespace Magento\Catalog\Test\Handler\CatalogCategory;
 
 use Mtf\Handler\HandlerInterface;
 
 /**
- * Interface CatalogCategoryEntityInterface
+ * Interface CatalogCategoryInterface
  */
-interface CatalogCategoryEntityInterface extends HandlerInterface
+interface CatalogCategoryInterface extends HandlerInterface
 {
     //
 }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategoryEntity/Curl.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategory/Curl.php
similarity index 95%
rename from dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategoryEntity/Curl.php
rename to dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategory/Curl.php
index f814fe009e5..9333090e28c 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategoryEntity/Curl.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogCategory/Curl.php
@@ -22,7 +22,7 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-namespace Magento\Catalog\Test\Handler\CatalogCategoryEntity;
+namespace Magento\Catalog\Test\Handler\CatalogCategory;
 
 use Mtf\System\Config;
 use Mtf\Fixture\FixtureInterface;
@@ -35,7 +35,7 @@ use Mtf\Util\Protocol\CurlTransport\BackendDecorator;
  * Class Curl
  * Create new category via curl
  */
-class Curl extends AbstractCurl implements CatalogCategoryEntityInterface
+class Curl extends AbstractCurl implements CatalogCategoryInterface
 {
     /**
      * Data use config for category
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogProductSimple/Curl.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogProductSimple/Curl.php
index b01de338626..e503bd54504 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogProductSimple/Curl.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Handler/CatalogProductSimple/Curl.php
@@ -65,10 +65,6 @@ class Curl extends AbstractCurl implements CatalogProductSimpleInterface
             'Search' => 3,
             'Catalog, Search' => 4
         ],
-        'tax_class_id' => [
-            'None' => 0,
-            'Taxable Goods' => 2
-        ],
         'website_ids' => [
             'Main Website' => 1
         ],
@@ -94,30 +90,28 @@ class Curl extends AbstractCurl implements CatalogProductSimpleInterface
         $prefix = isset($config['input_prefix']) ? $config['input_prefix'] : null;
         // @todo remove "if" when fixtures refactored
         if ($fixture instanceof InjectableFixture) {
-            $fields = $fixture->getData();
-            // Apply a placeholder for data
-            array_walk_recursive(
-                $fields,
-                function (&$item, $key, $placeholder) {
-                    $item = isset($placeholder[$key][$item]) ? $placeholder[$key][$item] : $item;
-                },
-                $this->placeholderData
-            );
-
+            $fields = $this->replacePlaceholder($fixture->getData(), $this->placeholderData);
+            // Getting Tax class id
+            if ($fixture->hasData('tax_class_id')) {
+                $taxClassId = $fixture->getDataFieldConfig('tax_class_id')['source']->getTaxClass()->getId();
+                $fields['tax_class_id'] = ($taxClassId === null)
+                    ? $this->getTaxClassId($fields['tax_class_id'])
+                    : $taxClassId;
+            }
             $fields = $this->prepareStockData($fields);
-
-            if ($prefix) {
-                $data[$prefix] = $fields;
-            } else {
-                $data = $fields;
+            if (!empty($fields['category_ids'])) {
+                $categoryIds = [];
+                foreach ($fields['category_ids'] as $categoryData) {
+                    $categoryIds[] = $categoryData['id'];
+                }
+                $fields['category_ids'] = $categoryIds;
             }
+
+            $data = $prefix ? [$prefix => $fields] : $fields;
         } else {
             $data = $this->_prepareData($fixture->getData('fields'), $prefix);
         }
 
-        if ($fixture->getData('category_id')) {
-            $data['product']['category_ids'] = $fixture->getData('category_id');
-        }
         $url = $this->_getUrl($config);
         $curl = new BackendDecorator(new CurlTransport(), new Config);
         $curl->addOption(CURLOPT_HEADER, 1);
@@ -133,6 +127,69 @@ class Curl extends AbstractCurl implements CatalogProductSimpleInterface
         return ['id' => $id];
     }
 
+    /**
+     * Getting tax class id from tax rule page
+     *
+     * @param string $taxClassName
+     * @return int
+     * @throws \Exception
+     */
+    protected function getTaxClassId($taxClassName)
+    {
+        $url = $_ENV['app_backend_url'] . 'tax/rule/new/';
+        $curl = new BackendDecorator(new CurlTransport(), new Config);
+        $curl->addOption(CURLOPT_HEADER, 1);
+        $curl->write(CurlInterface::POST, $url, '1.0', array(), array());
+        $response = $curl->read();
+        $curl->close();
+
+        preg_match('~<option value="(\d+)".*>' . $taxClassName . '</option>~', $response, $matches);
+        if (!isset($matches[1]) || empty($matches[1])) {
+            throw new \Exception('Product tax class id ' . $taxClassName . ' undefined!');
+        }
+
+        return (int)$matches[1];
+    }
+
+    /**
+     * Replace placeholder data in fixture data
+     *
+     * @param array $data
+     * @param array $placeholders
+     * @return array
+     */
+    private function replacePlaceholder(array $data, array $placeholders)
+    {
+        foreach ($data as $key => $value) {
+            if (!isset($placeholders[$key])) {
+                continue;
+            }
+            if (is_array($value)) {
+                $data[$key] = $this->replacePlaceholderValues($value, $placeholders[$key]);
+            } else {
+                $data[$key] = isset($placeholders[$key][$value]) ? $placeholders[$key][$value] : $value;
+            }
+        }
+        return $data;
+    }
+
+    /**
+     * Replace placeholder data in fixture values
+     *
+     * @param array $data
+     * @param array $placeholders
+     * @return array
+     */
+    private function replacePlaceholderValues(array $data, array $placeholders)
+    {
+        foreach ($data as $key => $value) {
+            if (isset($placeholders[$value])) {
+                $data[$key] = $placeholders[$value];
+            }
+        }
+        return $data;
+    }
+
     /**
      * Preparation of stock data
      *
@@ -151,7 +208,7 @@ class Curl extends AbstractCurl implements CatalogProductSimpleInterface
         if (empty($fields['stock_data']['qty'])) {
             $fields['stock_data']['qty'] = isset($fields['qty']) ? $fields['qty'] : null;
         }
-        if (!empty($fields['stock_data']['qty']) || !empty($fields['stock_data']['is_in_stock'])) {
+        if (!empty($fields['stock_data']['qty'])) {
             $fields['stock_data']['manage_stock'] = 1;
         }
 
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogCategoryEdit.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogCategoryEdit.php
new file mode 100644
index 00000000000..ebdd5e9d6ca
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogCategoryEdit.php
@@ -0,0 +1,81 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Page\Adminhtml;
+
+use Mtf\Page\BackendPage;
+
+/**
+ * Class CatalogCategoryEdit
+ * Category edit page on the Backend
+ */
+class CatalogCategoryEdit extends BackendPage
+{
+    const MCA = 'catalog/category/edit';
+
+    protected $_blocks = [
+        'messagesBlock' => [
+            'name' => 'messagesBlock',
+            'class' => 'Magento\Core\Test\Block\Messages',
+            'locator' => '#messages',
+            'strategy' => 'css selector',
+        ],
+        'formPageActions' => [
+            'name' => 'formPageActions',
+            'class' => 'Magento\Backend\Test\Block\FormPageActions',
+            'locator' => '.page-main-actions',
+            'strategy' => 'css selector',
+        ],
+        'editForm' => [
+            'name' => 'editForm',
+            'class' => 'Magento\Catalog\Test\Block\Adminhtml\Category\Edit\CategoryForm',
+            'locator' => '#category-edit-container',
+            'strategy' => 'css selector',
+        ],
+    ];
+
+    /**
+     * @return \Magento\Core\Test\Block\Messages
+     */
+    public function getMessagesBlock()
+    {
+        return $this->getBlockInstance('messagesBlock');
+    }
+
+    /**
+     * @return \Magento\Backend\Test\Block\FormPageActions
+     */
+    public function getFormPageActions()
+    {
+        return $this->getBlockInstance('formPageActions');
+    }
+
+    /**
+     * @return \Magento\Catalog\Test\Block\Adminhtml\Category\Edit\CategoryForm
+     */
+    public function getEditForm()
+    {
+        return $this->getBlockInstance('editForm');
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogCategoryEdit.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogCategoryEdit.xml
new file mode 100644
index 00000000000..7beb0035542
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogCategoryEdit.xml
@@ -0,0 +1,45 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="catalog/category/edit" >
+    <block>
+        <name>messagesBlock</name>
+        <class>Magento\Core\Test\Block\Messages</class>
+        <locator>#messages</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>formPageActions</name>
+        <class>Magento\Backend\Test\Block\FormPageActions</class>
+        <locator>.page-main-actions</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>editForm</name>
+        <class>Magento\Catalog\Test\Block\Adminhtml\Category\Edit\CategoryForm</class>
+        <locator>#category-edit-container</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeIndex.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeIndex.php
new file mode 100644
index 00000000000..43feaacbb2e
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeIndex.php
@@ -0,0 +1,80 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Page\Adminhtml;
+
+use Mtf\Page\BackendPage;
+
+/**
+ * Class CatalogProductAttributeIndex
+ */
+class CatalogProductAttributeIndex extends BackendPage
+{
+    const MCA = 'catalog/product_attribute/index';
+
+    protected $_blocks = [
+        'messagesBlock' => [
+            'name' => 'messageBlock',
+            'class' => 'Magento\Core\Test\Block\Messages',
+            'locator' => '#messages',
+            'strategy' => 'css selector',
+        ],
+        'pageActionsBlock' => [
+            'name' => 'pageActionsBlock',
+            'class' => 'Magento\Backend\Test\Block\GridPageActions',
+            'locator' => '.page-main-actions',
+            'strategy' => 'css selector',
+        ],
+        'grid' => [
+            'name' => 'grid',
+            'class' => 'Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Grid',
+            'locator' => '#attributeGrid',
+            'strategy' => 'css selector',
+        ],
+    ];
+
+    /**
+     * @return \Magento\Core\Test\Block\Messages
+     */
+    public function getMessageBlock()
+    {
+        return $this->getBlockInstance('messagesBlock');
+    }
+
+    /**
+     * @return \Magento\Backend\Test\Block\GridPageActions
+     */
+    public function getPageActionsBlock()
+    {
+        return $this->getBlockInstance('pageActionsBlock');
+    }
+
+    /**
+     * @return \Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Grid
+     */
+    public function getGrid()
+    {
+        return $this->getBlockInstance('grid');
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeIndex.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeIndex.xml
new file mode 100644
index 00000000000..a1f8a7b1c91
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeIndex.xml
@@ -0,0 +1,45 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="catalog/product_attribute/index">
+    <block>
+        <name>messagesBlock</name>
+        <class>Magento\Core\Test\Block\Messages</class>
+        <locator>#messages</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>pageActionsBlock</name>
+        <class>Magento\Backend\Test\Block\GridPageActions</class>
+        <locator>#page-main-actions</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>grid</name>
+        <class>Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Grid</class>
+        <locator>.grid</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeNew.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeNew.php
new file mode 100644
index 00000000000..5382c2babda
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeNew.php
@@ -0,0 +1,66 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\Page\Adminhtml;
+
+use Mtf\Page\BackendPage;
+
+/**
+ * Class CatalogProductAttributeNew
+ */
+class CatalogProductAttributeNew extends BackendPage
+{
+    const MCA = 'catalog/product_attribute/new';
+
+    protected $_blocks = [
+        'pageActions' => [
+            'name' => 'pageActions',
+            'class' => 'Magento\Backend\Test\Block\FormPageActions',
+            'locator' => '.page-main-actions',
+            'strategy' => 'css selector',
+        ],
+        'attributeForm' => [
+            'name' => 'attributeForm',
+            'class' => 'Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Edit\AttributeForm',
+            'locator' => '[id$="main-container"]',
+            'strategy' => 'css selector',
+        ],
+    ];
+
+    /**
+     * @return \Magento\Backend\Test\Block\FormPageActions
+     */
+    public function getPageActions()
+    {
+        return $this->getBlockInstance('pageActions');
+    }
+
+    /**
+     * @return \Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Edit\AttributeForm
+     */
+    public function getAttributeForm()
+    {
+        return $this->getBlockInstance('attributeForm');
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeNew.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeNew.xml
new file mode 100644
index 00000000000..7d9ab62e855
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductAttributeNew.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="catalog/product_attribute/new">
+    <block>
+        <name>pageActions</name>
+        <class>Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\FormPageActions</class>
+        <locator>.page-main-actions</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>attributeForm</name>
+        <class>Magento\Catalog\Test\Block\Adminhtml\Product\Attribute\Edit\AttributeForm</class>
+        <locator>#edit_form</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductEdit.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductEdit.php
index 5b8c8adce31..62ba2d4ec7d 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductEdit.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductEdit.php
@@ -36,7 +36,7 @@ class CatalogProductEdit extends BackendPage
     protected $_blocks = [
         'form' => [
             'name' => 'form',
-            'class' => 'Magento\Catalog\Test\Block\Adminhtml\Product\Form',
+            'class' => 'Magento\Catalog\Test\Block\Adminhtml\Product\ProductForm',
             'locator' => '[id="page:main-container"]',
             'strategy' => 'css selector',
         ],
@@ -75,7 +75,7 @@ class CatalogProductEdit extends BackendPage
     }
 
     /**
-     * @return \Magento\Catalog\Test\Block\Adminhtml\Product\Form
+     * @return \Magento\Catalog\Test\Block\Adminhtml\Product\ProductForm
      */
     public function getForm()
     {
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductEdit.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductEdit.xml
index e4817fb8507..c845c7c266f 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductEdit.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductEdit.xml
@@ -26,7 +26,7 @@
 <page mca="catalog/product/edit" >
     <block>
         <name>form</name>
-        <class>Magento\Catalog\Test\Block\Adminhtml\Product\Form</class>
+        <class>Magento\Catalog\Test\Block\Adminhtml\Product\ProductForm</class>
         <locator>[id="page:main-container"]</locator>
         <strategy>css selector</strategy>
     </block>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductNew.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductNew.php
index 18ce4f877aa..242071a9dfe 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductNew.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductNew.php
@@ -37,7 +37,7 @@ class CatalogProductNew extends BackendPage
     protected $_blocks = [
         'form' => [
             'name' => 'form',
-            'class' => 'Magento\Catalog\Test\Block\Adminhtml\Product\Form',
+            'class' => 'Magento\Catalog\Test\Block\Adminhtml\Product\ProductForm',
             'locator' => '[id="page:main-container"]',
             'strategy' => 'css selector',
         ],
@@ -82,8 +82,10 @@ class CatalogProductNew extends BackendPage
     }
 
     /**
+     * Page initialization
      *
      * @param FixtureInterface $fixture
+     * @return void
      */
     public function init(FixtureInterface $fixture)
     {
@@ -104,7 +106,7 @@ class CatalogProductNew extends BackendPage
     }
 
     /**
-     * @return \Magento\Catalog\Test\Block\Adminhtml\Product\Form
+     * @return \Magento\Catalog\Test\Block\Adminhtml\Product\ProductForm
      */
     public function getForm()
     {
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductNew.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductNew.xml
index a9b7418dceb..fc846ca6ba1 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductNew.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Adminhtml/CatalogProductNew.xml
@@ -26,7 +26,7 @@
 <page mca="catalog/product/new" >
     <block>
         <name>form</name>
-        <class>Magento\Catalog\Test\Block\Adminhtml\Product\Form</class>
+        <class>Magento\Catalog\Test\Block\Adminhtml\Product\ProductForm</class>
         <locator>[id="page:main-container"]</locator>
         <strategy>css selector</strategy>
     </block>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategory.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategory.php
index 168a44778cc..0184cbca19b 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategory.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategory.php
@@ -31,7 +31,6 @@ use Mtf\Client\Element\Locator;
 /**
  * Class CatalogCategory
  * Manage categories page in backend
- *
  */
 class CatalogCategory extends Page
 {
@@ -91,11 +90,11 @@ class CatalogCategory extends Page
     /**
      * Get Category edit form
      *
-     * @return \Magento\Catalog\Test\Block\Adminhtml\Category\Edit\Form
+     * @return \Magento\Catalog\Test\Block\Adminhtml\Category\Edit\CategoryForm
      */
     public function getFormBlock()
     {
-        return Factory::getBlockFactory()->getMagentoCatalogAdminhtmlCategoryEditForm(
+        return Factory::getBlockFactory()->getMagentoCatalogAdminhtmlCategoryEditCategoryForm(
             $this->_browser->find($this->formBlock, Locator::SELECTOR_CSS)
         );
     }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryEdit.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryEdit.php
index 3dc39db826d..ddfbd0b2ded 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryEdit.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryEdit.php
@@ -32,7 +32,6 @@ use Magento\Backend\Test\Block\FormPageActions;
 /**
  * Class CatalogCategoryEdit
  * Edit category page in backend
- *
  */
 class CatalogCategoryEdit extends Page
 {
@@ -99,11 +98,11 @@ class CatalogCategoryEdit extends Page
     /**
      * Get Category edit form
      *
-     * @return \Magento\Catalog\Test\Block\Adminhtml\Category\Edit\Form
+     * @return \Magento\Catalog\Test\Block\Adminhtml\Category\Edit\CategoryForm
      */
     public function getFormBlock()
     {
-        return Factory::getBlockFactory()->getMagentoCatalogAdminhtmlCategoryEditForm(
+        return Factory::getBlockFactory()->getMagentoCatalogAdminhtmlCategoryEditCategoryForm(
             $this->_browser->find($this->formBlock, Locator::SELECTOR_CSS)
         );
     }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryView.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryView.php
index 825424bcce1..05dae7f2921 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryView.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryView.php
@@ -56,7 +56,19 @@ class CatalogCategoryView extends FrontendPage
         'toolbar' => [
             'name' => 'toolbar',
             'class' => 'Magento\Catalog\Test\Block\Product\ProductList\Toolbar',
-            'locator' => '.pages .items',
+            'locator' => '.toolbar.products',
+            'strategy' => 'css selector',
+        ],
+        'titleBlock' => [
+            'name' => 'titleBlock',
+            'class' => 'Magento\Theme\Test\Block\Html\Title',
+            'locator' => '.page.title h1.title',
+            'strategy' => 'css selector',
+        ],
+        'viewBlock' => [
+            'name' => 'descriptionBlock',
+            'class' => 'Magento\Catalog\Test\Block\Category\View',
+            'locator' => '.category.view',
             'strategy' => 'css selector',
         ]
     ];
@@ -92,4 +104,20 @@ class CatalogCategoryView extends FrontendPage
     {
         return $this->getBlockInstance('toolbar');
     }
+
+    /**
+     * @return \Magento\Theme\Test\Block\Html\Title
+     */
+    public function getTitleBlock()
+    {
+        return $this->getBlockInstance('titleBlock');
+    }
+
+    /**
+     * @return \Magento\Catalog\Test\Block\Category\View
+     */
+    public function getViewBlock()
+    {
+        return $this->getBlockInstance('viewBlock');
+    }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryView.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryView.xml
index 659960ed355..1ac146ad826 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryView.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Page/Category/CatalogCategoryView.xml
@@ -48,4 +48,16 @@
         <locator>.pages .items</locator>
         <strategy>css selector</strategy>
     </block>
+    <block>
+        <name>titleBlock</name>
+        <class>Magento\Theme\Test\Block\Html\Title</class>
+        <locator>.page.title h1.title</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>viewBlock</name>
+        <class>Magento\Catalog\Test\Block\Category\View</class>
+        <locator>.category.view</locator>
+        <strategy>css selector</strategy>
+    </block>
 </page>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/CatalogCategoryEntity.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/CatalogCategory.php
similarity index 94%
rename from dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/CatalogCategoryEntity.php
rename to dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/CatalogCategory.php
index d46e139e675..7cf65ab2382 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/CatalogCategoryEntity.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/CatalogCategory.php
@@ -27,10 +27,10 @@ namespace Magento\Catalog\Test\Repository;
 use Mtf\Repository\AbstractRepository;
 
 /**
- * Class CatalogCategoryEntity
+ * Class CatalogCategory
  * Data for creation Category
  */
-class CatalogCategoryEntity extends AbstractRepository
+class CatalogCategory extends AbstractRepository
 {
     public function __construct(array $defaultConfig = [], array $defaultData = [])
     {
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/CatalogProductSimple.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/CatalogProductSimple.php
index a80d41a6033..2fa30e1e301 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/CatalogProductSimple.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/Repository/CatalogProductSimple.php
@@ -34,53 +34,156 @@ class CatalogProductSimple extends AbstractRepository
 {
     public function __construct(array $defaultConfig = [], array $defaultData = [])
     {
+        $this->_data['default'] = [
+            'type_id' => 'simple',
+            'attribute_set_id' => 'Default',
+            'name' => 'Simple Product %isolation%',
+            'sku' => 'sku_simple_product_%isolation%',
+            'weight' => 1,
+            'quantity_and_stock_status' => 'In Stock',
+            'qty' => 25,
+            'price' => ['value' => 560, 'preset' => '-'],
+            'website_ids' => ['Main Website'],
+        ];
+
         $this->_data['100_dollar_product'] = [
             'sku' => '100_dollar_product%isolation%',
             'name' => '100_dollar_product%isolation%',
             'type_id' => 'simple',
-            'attribute_set_id' => '4',
+            'attribute_set_id' => 'Default',
+            'quantity_and_stock_status' => 'In Stock',
             'price' => ['value' => 100, 'preset' => '-'],
+            'website_ids' => ['Main Website'],
         ];
 
         $this->_data['40_dollar_product'] = [
             'sku' => '40_dollar_product',
             'name' => '40_dollar_product',
             'type_id' => 'simple',
-            'attribute_set_id' => '4',
+            'attribute_set_id' => 'Default',
+            'quantity_and_stock_status' => 'In Stock',
             'price' => ['value' => 40, 'preset' => '-'],
             'id' => '2',
-            'mtf_dataset_name' => '40_dollar_product'
+            'mtf_dataset_name' => '40_dollar_product',
+            'website_ids' => ['Main Website'],
         ];
 
         $this->_data['MAGETWO-23036'] = [
             'sku' => 'MAGETWO-23036',
             'name' => 'simple_with_category',
             'type_id' => 'simple',
-            'attribute_set_id' => '4',
+            'attribute_set_id' => 'Default',
+            'quantity_and_stock_status' => 'In Stock',
             'price' => ['value' => 100, 'preset' => 'MAGETWO-23036'],
             'id' => '3',
             'category_ids' => ['presets' => 'default'],
-            'mtf_dataset_name' => 'simple_with_category'
+            'mtf_dataset_name' => 'simple_with_category',
+            'website_ids' => ['Main Website'],
         ];
 
         $this->_data['product_with_category'] = [
             'sku' => 'simple_product_with_category_%isolation%',
             'name' => 'Simple product with category %isolation%',
             'type_id' => 'simple',
-            'attribute_set_id' => '4',
+            'attribute_set_id' => 'Default',
+            'price' => ['value' => 100, 'preset' => ''],
+            'category_ids' => ['presets' => 'default_subcategory'],
+            'website_ids' => ['Main Website'],
+            'mtf_dataset_name' => 'simple_with_category',
+        ];
+
+        $this->_data['simple_for_salesrule_1'] = [
+            'type_id' => 'simple',
+            'attribute_set_id' => 'Default',
+            'quantity_and_stock_status' => 'In Stock',
+            'name' => 'Simple Product %isolation%',
+            'sku' => 'sku_simple_product_%isolation%',
             'price' => ['value' => 100, 'preset' => ''],
+            'weight' => 100,
+            'website_ids' => ['Main Website'],
             'category_ids' => ['presets' => 'default_subcategory']
         ];
 
-        $this->_data['default'] = [
+        $this->_data['simple_for_salesrule_2'] = [
             'type_id' => 'simple',
             'attribute_set_id' => 'Default',
             'name' => 'Simple Product %isolation%',
             'sku' => 'sku_simple_product_%isolation%',
-            'weight' => 1,
+            'price' => ['value' => 50, 'preset' => ''],
+            'weight' => 50,
+            'website_ids' => ['Main Website'],
+            'category_ids' => ['presets' => 'default_subcategory']
+        ];
+
+        $this->_data['product_with_special_price_and_category'] = [
+            'sku' => 'simple_product_with_special_price_and_category%isolation%',
+            'name' => 'Simple product with special price and category %isolation%',
+            'type_id' => 'simple',
+            'attribute_set_id' => 'Default',
+            'price' => ['value' => 100, 'preset' => ''],
+            'special_price' => 90,
+            'category_ids' => ['presets' => 'default_subcategory'],
+            'website_ids' => ['Main Website'],
+        ];
+
+        $this->_data['adc_123_simple_for_advancedsearch'] = [
+            'name' => 'adc_123',
+            'sku' => 'adc_123',
+            'price' => ['value' => 100.00, 'preset' => '-'],
+            'tax_class_id' => ['dataSet' => 'None'],
+            'quantity_and_stock_status' => [
+                'qty' => 666,
+                'is_in_stock' => 'Yes',
+            ],
+            'weight' => 1.0000,
+            'description' => '<p>dfj_full</p>',
+            'status' => 'Product online',
+            'website_ids' => [
+                0 => 'Main Website',
+            ],
+            'stock_data' => [
+                'manage_stock' => 'Yes',
+                'original_inventory_qty' => 666,
+                'qty' => 666.0000,
+                'is_in_stock' => 'In Stock',
+            ],
+            'visibility' => 'Catalog, Search',
+        ];
+
+        $this->_data['abc_dfj_simple_for_advancedsearch'] = [
+            'name' => 'abc_dfj',
+            'sku' => 'abc_dfj',
+            'price' => ['value' => 50.00, 'preset' => '-'],
+            'tax_class_id' => ['dataSet' => 'Taxable Goods'],
+            'quantity_and_stock_status' => [
+                'qty' => 666.0000,
+                'is_in_stock' => 'In Stock',
+            ],
+            'weight' => 1.0000,
+            'description' => '<p>adc_Full</p>',
+            'status' => 'Product online',
+            'short_description' => '<p>abc_short</p>',
+            'website_ids' => [
+                0 => 'Main Website',
+            ],
+            'stock_data' => [
+                'manage_stock' => 'Yes',
+                'original_inventory_qty' => 666,
+                'qty' => 666.0000,
+                'is_in_stock' => 'Yes',
+            ],
+            'visibility' => 'Catalog, Search',
+        ];
+
+        $this->_data['100_dollar_product_for_tax_rule'] = [
+            'sku' => '100_dollar_product%isolation%',
+            'name' => '100_dollar_product%isolation%',
+            'type_id' => 'simple',
+            'attribute_set_id' => 'Default',
             'quantity_and_stock_status' => 'In Stock',
             'qty' => 25,
-            'price' => ['value' => 560, 'preset' => '-'],
+            'price' => ['value' => 100, 'preset' => '-'],
+            'website_ids' => ['Main Website'],
         ];
     }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Category/UpdateCategoryEntityTest.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Category/UpdateCategoryEntityTest.php
new file mode 100644
index 00000000000..0743df162b4
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Category/UpdateCategoryEntityTest.php
@@ -0,0 +1,102 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\TestCase\Category;
+
+use Magento\Catalog\Test\Fixture\CatalogCategory;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Catalog\Test\Page\Adminhtml\CatalogCategoryIndex;
+use Magento\Catalog\Test\Page\Adminhtml\CatalogCategoryEdit;
+use Mtf\TestCase\Injectable;
+
+/**
+ * Test Creation for UpdateCategoryEntity
+ *
+ * Test Flow:
+ * Preconditions:
+ * 1. Create category
+ *
+ * Steps:
+ * 1. Login as admin
+ * 2. Navigate Products->Categories
+ * 3. Open category created in preconditions
+ * 4. Update data according to data set
+ * 5. Save
+ * 6. Perform asserts
+ *
+ * @group Category_Management_(MX)
+ * @ZephyrId MAGETWO-23290
+ */
+class UpdateCategoryEntityTest extends Injectable
+{
+    /**
+     * Catalog category index page
+     *
+     * @var CatalogCategoryIndex
+     */
+    protected $catalogCategoryIndex;
+
+    /**
+     * Catalog category edit page
+     *
+     * @var CatalogCategoryEdit
+     */
+    protected $catalogCategoryEdit;
+
+    /**
+     * Inject page end prepare default category
+     *
+     * @param CatalogCategory $initialCategory
+     * @param CatalogCategoryIndex $catalogCategoryIndex
+     * @param CatalogCategoryEdit $catalogCategoryEdit
+     * @return array
+     */
+    public function __inject(
+        CatalogCategory $initialCategory,
+        CatalogCategoryIndex $catalogCategoryIndex,
+        CatalogCategoryEdit $catalogCategoryEdit
+    ) {
+        $this->catalogCategoryIndex = $catalogCategoryIndex;
+        $this->catalogCategoryEdit = $catalogCategoryEdit;
+        $initialCategory->persist();
+        return ['initialCategory' => $initialCategory];
+    }
+
+    /**
+     * Test for update category
+     *
+     * @param CatalogCategory $category
+     * @param CatalogCategory $initialCategory
+     * @return void
+     */
+    public function testUpdateCategory(CatalogCategory $category, CatalogCategory $initialCategory)
+    {
+        $this->catalogCategoryIndex->open();
+        $this->catalogCategoryIndex->getTreeCategories()->selectCategory(
+            $initialCategory->getPath() . '/' . $initialCategory->getName()
+        );
+        $this->catalogCategoryEdit->getEditForm()->fill($category);
+        $this->catalogCategoryEdit->getFormPageActions()->save();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Category/UpdateCategoryEntityTest/testUpdateCategory.csv b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Category/UpdateCategoryEntityTest/testUpdateCategory.csv
new file mode 100644
index 00000000000..269b08ebd8d
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Category/UpdateCategoryEntityTest/testUpdateCategory.csv
@@ -0,0 +1,4 @@
+"category/data/name";"category/data/is_active";"category/data/url_key";"category/data/description";"category/data/meta_title";"category/data/include_in_menu";"category/data/available_product_listing_config";"category/data/available_sort_by/sort_2";"category/data/available_sort_by/sort_1";"category/data/default_product_listing_config";"category/data/default_sort_by";"constraint"
+"Name%isolation%";"Yes";"UrlKey%isolation%";"-";"-";"Yes";"Yes";"-";"-";"No";"Name";"assertCategorySaveMessage, assertCategoryForm, assertCategoryPage "
+"Name%isolation%";"Yes";"UrlKey%isolation%";"Category Description";"Category Title";"Yes";"No";"Position";"Price";"Yes";"-";"assertCategorySaveMessage, assertCategoryForm, assertCategoryPage "
+"Name%isolation%";"No";"-";"-";"-";"-";"-";"-";"-";"-";"-";"assertCategorySaveMessage, assertCategoryForm"
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/CreateVirtualProductEntityTest.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/CreateVirtualProductEntityTest.php
index 3a1aa1f7584..939f39a411a 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/CreateVirtualProductEntityTest.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/CreateVirtualProductEntityTest.php
@@ -25,7 +25,7 @@
 namespace Magento\Catalog\Test\TestCase\Product;
 
 use Mtf\TestCase\Injectable;
-use Magento\Catalog\Test\Fixture\CatalogCategoryEntity;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 use Magento\Catalog\Test\Fixture\CatalogProductVirtual;
 use Magento\Catalog\Test\Page\Adminhtml\CatalogProductNew;
 use Magento\Catalog\Test\Page\Adminhtml\CatalogProductIndex;
@@ -49,7 +49,7 @@ class CreateVirtualProductEntityTest extends Injectable
     /**
      * Category fixture
      *
-     * @var CatalogCategoryEntity
+     * @var CatalogCategory
      */
     protected $category;
 
@@ -70,10 +70,10 @@ class CreateVirtualProductEntityTest extends Injectable
     /**
      * Prepare data
      *
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @return array
      */
-    public function __prepare(CatalogCategoryEntity $category)
+    public function __prepare(CatalogCategory $category)
     {
         $category->persist();
         return [
@@ -98,10 +98,10 @@ class CreateVirtualProductEntityTest extends Injectable
      * Run create product virtual entity test
      *
      * @param CatalogProductVirtual $product
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @return void
      */
-    public function testCreate(CatalogProductVirtual $product, CatalogCategoryEntity $category)
+    public function testCreate(CatalogProductVirtual $product, CatalogCategory $category)
     {
         // Steps
         $this->productGrid->open();
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/CreateVirtualProductEntityTest/testCreate.csv b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/CreateVirtualProductEntityTest/testCreate.csv
index 472cffe476a..2e81c0aad84 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/CreateVirtualProductEntityTest/testCreate.csv
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/CreateVirtualProductEntityTest/testCreate.csv
@@ -1,4 +1,4 @@
-"product/data/name";"product/data/sku";"product/data/price/value";"product/data/tax_class_id";"product/data/qty";"product/data/is_virtual";"product/data/category";"product/data/group_price/preset";"product/data/price/preset";"product/data/tier_price/preset";"product/data/inventory_manage_stock";"product/data/quantity_and_stock_status";"product/data/custom_options/preset";"product/data/visibility";"constraint"
+"product/data/name";"product/data/sku";"product/data/price/value";"product/data/tax_class_id/dataSet";"product/data/qty";"product/data/is_virtual";"product/data/category";"product/data/group_price/preset";"product/data/price/preset";"product/data/tier_price/preset";"product/data/inventory_manage_stock";"product/data/quantity_and_stock_status";"product/data/custom_options/preset";"product/data/visibility";"constraint"
 "VirtualProduct %isolation%";"virtual_sku_%isolation%";"10";"-";"-";"Yes";"-";"-";"-";"-";"-";"-";"-";"-";"assertProductSaveMessage, assertProductInGrid"
 "VirtualProduct %isolation%";"virtual_sku_%isolation%";"10";"None";"999";"Yes";"category_%isolation%";"-";"-";"MAGETWO-23002";"Yes";"In Stock";"-";"Catalog, Search";"assertProductSaveMessage, assertProductVisibleInCategory, assertProductForm, assertProductSearchableBySku"
 "VirtualProduct %isolation%";"-";"10";"Taxable Goods";"999";"Yes";"-";"-";"MAGETWO-23030";"-";"-";"Out of Stock";"-";"Search";"assertProductSaveMessage, assertProductForm, assertProductSkuAutoGenerated, assertProductSearchableBySku"
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/UpdateSimpleProductEntityTest.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/UpdateSimpleProductEntityTest.php
index 47137116163..2b63d75ec3f 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/UpdateSimpleProductEntityTest.php
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/Product/UpdateSimpleProductEntityTest.php
@@ -27,7 +27,7 @@ namespace Magento\Catalog\Test\TestCase\Product;
 use Mtf\TestCase\Injectable;
 use Mtf\Fixture\FixtureFactory;
 use Magento\Catalog\Test\Fixture\CatalogProductSimple;
-use Magento\Catalog\Test\Fixture\CatalogCategoryEntity;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 use Magento\Catalog\Test\Page\Adminhtml\CatalogProductEdit;
 use Magento\Catalog\Test\Page\Adminhtml\CatalogProductIndex;
 
@@ -77,10 +77,10 @@ class UpdateSimpleProductEntityTest extends Injectable
     /**
      * Prepare data
      *
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @return array
      */
-    public function __prepare(CatalogCategoryEntity $category)
+    public function __prepare(CatalogCategory $category)
     {
         $category->persist();
         return [
@@ -93,14 +93,14 @@ class UpdateSimpleProductEntityTest extends Injectable
      *
      * @param CatalogProductIndex $productGrid
      * @param CatalogProductEdit $editProductPage
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @param FixtureFactory $fixtureFactory
      * @return array
      */
     public function __inject(
         CatalogProductIndex $productGrid,
         CatalogProductEdit $editProductPage,
-        CatalogCategoryEntity $category,
+        CatalogCategory $category,
         FixtureFactory $fixtureFactory
     ) {
         $this->product = $fixtureFactory->createByCode(
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/CreateProductAttributeEntityTest.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/CreateProductAttributeEntityTest.php
new file mode 100644
index 00000000000..e26c7edcec4
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/CreateProductAttributeEntityTest.php
@@ -0,0 +1,67 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\TestCase\ProductAttribute;
+
+use Mtf\TestCase\Injectable;
+use Magento\Catalog\Test\Fixture\CatalogProductAttribute;
+use Magento\Catalog\Test\Page\Adminhtml\CatalogProductAttributeIndex;
+use Magento\Catalog\Test\Page\Adminhtml\CatalogProductAttributeNew;
+
+/**
+ * Test Creation for CreateProductAttributeEntity
+ *
+ * Test Flow:
+ * 1. Log in to Backend.
+ * 2. Navigate to Stores > Attributes > Product.
+ * 3. Start to create new Product Attribute.
+ * 4. Fill out fields data according to data set.
+ * 5. Save Product Attribute.
+ * 6. Perform appropriate assertions.
+ *
+ * @group Product_Attributes_(CS)
+ * @ZephyrId MAGETWO-24767
+ */
+class CreateProductAttributeEntityTest extends Injectable
+{
+    /**
+     * Run CreateProductAttributeEntity test
+     *
+     * @param CatalogProductAttribute $productAttribute
+     * @param CatalogProductAttributeIndex $attributeIndex
+     * @param CatalogProductAttributeNew $attributeNew
+     * @return void
+     */
+    public function testCreateProductAttribute(
+        CatalogProductAttribute $productAttribute,
+        CatalogProductAttributeIndex $attributeIndex,
+        CatalogProductAttributeNew $attributeNew
+    ) {
+        //Steps
+        $attributeIndex->open();
+        $attributeIndex->getPageActionsBlock()->addNew();
+        $attributeNew->getAttributeForm()->fill($productAttribute);
+        $attributeNew->getPageActions()->save();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/CreateProductAttributeEntityTest/testCreateProductAttribute.csv b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/CreateProductAttributeEntityTest/testCreateProductAttribute.csv
new file mode 100644
index 00000000000..4dd1b7bc9e9
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/CreateProductAttributeEntityTest/testCreateProductAttribute.csv
@@ -0,0 +1,9 @@
+"productAttribute/data/frontend_label";"productAttribute/data/frontend_input";"productAttribute/data/options/preset";"productAttribute/data/is_required";"productAttribute/data/attribute_code";"productAttribute/data/is_global";"productAttribute/data/default_value_text";"productAttribute/data/is_unique";"productAttribute/data/is_configurable";"productAttribute/data/manage_frontend_label";"productAttribute/data/is_searchable";"productAttribute/data/is_visible_in_advanced_search";"productAttribute/data/is_comparable";"productAttribute/data/is_filterable";"productAttribute/data/is_filterable_in_search";"productAttribute/data/is_used_for_promo_rules";"productAttribute/data/is_html_allowed_on_front";"productAttribute/data/is_visible_on_front";"productAttribute/data/used_in_product_listing";"productAttribute/data/used_for_sort_by";"constraint"
+"Text_Field_Admin_%isolation%";"Text Field";"-";"No";"attr_textfield_%isolation%";"-";"-";"-";"-";"-";"-";"-";"-";"-";"-";"-";"-";"-";"-";"-";"assertProductAttributeSaveMessage, assertProductAttributeInGrid, assertAttributeOnAttributeForm, assertProductAttributeOnProductForm"
+"Text_Field_Admin_%isolation%";"Text Area";"-";"Yes";"attr_textarea_%isolation%";"Store View";"default_value_text%isolation%";"No";"-";"Area_Field%isolation%";"Yes";"Yes";"Yes";"-";"-";"-";"-";"-";"-";"-";"assertProductAttributeSaveMessage, assertProductAttributeInGrid, assertAttributeOnAttributeForm, assertProductAttributeOnProductForm, assertProductAttributeIsRequired, assertAttributeSearchableByLabel, assertProductAttributeIsUnique, assertProductAttributeDisplayingOnSearchForm, assertProductAttributeIsComparable"
+"Date_Admin_%isolation%";"Date";"-";"No";"attr_date_%isolation%";"-";"%currentDate%";"No";"-";"Date_Store_View";"No";"No";"No";"-";"-";"Yes";"-";"Yes";"Yes";"Yes";"assertProductAttributeSaveMessage, assertProductAttributeInGrid, assertAttributeOnAttributeForm, assertProductAttributeOnProductForm, assertProductAttributeUsedSortOnFrontend, assertProductAttributeIsUsedPromoRules "
+"Yes/No_Admin_%isolation%";"Yes/No";"-";"Yes";"attr_yesno_%isolation%";"Global";"No";"-";"-";"Yes/No_Global";"-";"-";"-";"-";"-";"-";"No";"No";"No";"No";"assertProductAttributeSaveMessage, assertProductAttributeInGrid, assertAttributeOnAttributeForm, assertProductAttributeOnProductForm"
+"Multiple_Select_Admin_%isolation%";"Multiple Select";"default";"Yes";"attr_multiselect_%isolation%";"Website";"-";"Yes";"-";"-";"Yes";"Yes";"Yes";"Filterable (with results)";"Yes";"-";"Yes";"Yes";"Yes";"-";"assertProductAttributeSaveMessage, assertProductAttributeInGrid, assertAttributeOnAttributeForm, assertProductAttributeOnProductForm, assertProductAttributeIsRequired, assertProductAttributeIsUnique, assertProductAttributeDisplayingOnFrontend, assertProductAttributeDisplayingOnSearchForm, assertProductAttributeIsComparable, assertProductAttributeIsHtmlAllowed, assertProductAttributeIsFilterable, assertProductAttributeIsFilterableInSearch, assertAttributeSearchableByLabel, assertAttributeOptionsOnProductForm"
+"Dropdown_Admin_%isolation%";"Dropdown";"default";"Yes";"attr_dropdown_%isolation%";"Global";"-";"No";"Yes";"-";"Yes";"Yes";"Yes";"Filterable (with results)";"Yes";"-";"Yes";"Yes";"Yes";"Yes";"assertProductAttributeSaveMessage, assertProductAttributeInGrid, assertAttributeOnAttributeForm, assertProductAttributeOnProductForm, assertProductAttributeIsRequired, assertProductAttributeIsGlobal, assertProductAttributeDisplayingOnFrontend, assertProductAttributeDisplayingOnSearchForm, assertAttributeSearchableByLabel, assertProductAttributeIsComparable, assertProductAttributeIsHtmlAllowed, assertProductAttributeUsedSortOnFrontend, assertProductAttributeIsFilterable, assertProductAttributeIsConfigurable, assertProductAttributeIsFilterableInSearch, assertAttributeOptionsOnProductForm"
+"Price_Admin_%isolation%";"Price";"-";"No";"attr_price_%isolation%";"-";"-";"No";"-";"Price_StoreView";"Yes";"Yes";"No";"Filterable (with results)";"Yes";"-";"-";"-";"-";"-";"assertProductAttributeSaveMessage, assertProductAttributeInGrid, assertAttributeOnAttributeForm, assertProductAttributeOnProductForm, assertAttributeSearchableByLabel, assertProductAttributeDisplayingOnSearchForm, assertProductAttributeIsFilterable, assertProductAttributeIsFilterableInSearch"
+"Fixed_Product_Tax_Admin_%isolation%";"Fixed Product Tax";"-";"No";"attr_fpt_code_%isolation%";"-";"-";"-";"-";"Fixed_Product_Tax_Storeview";"-";"-";"-";"-";"-";"-";"-";"-";"-";"-";"assertProductAttributeSaveMessage, assertProductAttributeInGrid, assertAttributeOnAttributeForm, assertProductAttributeOnProductForm"
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/DeleteSystemProductAttributeTest.php b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/DeleteSystemProductAttributeTest.php
new file mode 100644
index 00000000000..c6d2ef81a59
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/DeleteSystemProductAttributeTest.php
@@ -0,0 +1,63 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Test\TestCase\ProductAttribute;
+
+use Mtf\TestCase\Injectable;
+use Magento\Catalog\Test\Fixture\CatalogProductAttribute;
+use Magento\Catalog\Test\Page\Adminhtml\CatalogProductAttributeIndex;
+
+/**
+ * Cover DeleteSystemProductAttribute with functional tests designed for automation
+ *
+ * Test Flow:
+ * 1. Log in as default admin user.
+ * 2. Go to Stores > Attributes > Product.
+ * 3. Search system product attribute in grid by given data.
+ * 4. Click on line with search results.
+ * 5. Perform assertion.
+ *
+ * @group Product_Attributes_(MX)
+ * @ZephyrId MAGETWO-24771
+ */
+class DeleteSystemProductAttributeTest extends Injectable
+{
+    /**
+     * Run delete system product attribute test
+     *
+     * @param CatalogProductAttribute $productAttribute
+     * @param CatalogProductAttributeIndex $attributeIndex
+     * @return void
+     */
+    public function testDeleteSystemProductAttribute(
+        CatalogProductAttribute $productAttribute,
+        CatalogProductAttributeIndex $attributeIndex
+    ) {
+        $filter = $productAttribute->getData();
+
+        // Steps
+        $attributeIndex->open();
+        $attributeIndex->getGrid()->searchAndOpen($filter);
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/DeleteSystemProductAttributeTest/testDeleteSystemProductAttribute.csv b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/DeleteSystemProductAttributeTest/testDeleteSystemProductAttribute.csv
new file mode 100644
index 00000000000..47b66754f27
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/TestCase/ProductAttribute/DeleteSystemProductAttributeTest/testDeleteSystemProductAttribute.csv
@@ -0,0 +1,2 @@
+"productAttribute/data/attribute_code";"productAttribute/data/is_user_defined";"constraint"
+"news_from_date";"Yes";"assertAbsenceDeleteAttributeButton" 
\ No newline at end of file
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/curl/di.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/curl/di.xml
index 6ae8871cff4..e916678bd8c 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/curl/di.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/curl/di.xml
@@ -25,5 +25,5 @@
 -->
 <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../../../../lib/internal/Magento/Framework/ObjectManager/etc/config.xsd">
     <preference for="Magento\Catalog\Test\Handler\CatalogProductSimple\CatalogProductSimpleInterface" type="\Magento\Catalog\Test\Handler\CatalogProductSimple\Curl" />
-    <preference for="Magento\Catalog\Test\Handler\CatalogCategoryEntity\CatalogCategoryEntityInterface" type="\Magento\Catalog\Test\Handler\CatalogCategoryEntity\Curl" />
+    <preference for="Magento\Catalog\Test\Handler\CatalogCategory\CatalogCategoryInterface" type="\Magento\Catalog\Test\Handler\CatalogCategory\Curl" />
 </config>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/constraint.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/constraint.xml
index a197598be46..fc50ecd0876 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/constraint.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/constraint.xml
@@ -56,7 +56,7 @@
         <require>
             <catalogCategoryView class="Magento\Catalog\Test\Page\Category\CatalogCategoryView" />
             <cmsIndex class="Magento\Cms\Test\Page\CmsIndex" />
-            <category class="Magento\Catalog\Test\Fixture\CatalogCategoryEntity" />
+            <category class="Magento\Catalog\Test\Fixture\CatalogCategory" />
             <product class="Mtf\Fixture\FixtureInterface" />
         </require>
     </assertProductVisibleInCategory>
@@ -74,7 +74,7 @@
             <catalogCategoryView class="Magento\Catalog\Test\Page\Category\CatalogCategoryView" />
             <cmsIndex class="Magento\Cms\Test\Page\CmsIndex" />
             <product class="Mtf\Fixture\FixtureInterface" />
-            <category class="Magento\Catalog\Test\Fixture\CatalogCategoryEntity" />
+            <category class="Magento\Catalog\Test\Fixture\CatalogCategory" />
         </require>
     </assertProductInCategory>
     <assertProductInCart module="Magento_Catalog">
@@ -129,11 +129,9 @@
     </assertProductForm>
     <assertAddToCartButtonAbsent module="Magento_Catalog">
         <severeness>low</severeness>
-        <require></require>
     </assertAddToCartButtonAbsent>
     <assertAddToCartButtonPresent module="Magento_Catalog">
         <severeness>low</severeness>
-        <require></require>
     </assertAddToCartButtonPresent>
     <assertProductIsNotDisplayingOnFrontend module="Magento_Catalog">
         <severeness>low</severeness>
@@ -141,7 +139,7 @@
             <catalogCategoryView class="Magento\Catalog\Test\Page\Category\CatalogCategoryView" />
             <cmsIndex class="Magento\Cms\Test\Page\CmsIndex" />
             <product class="Mtf\Fixture\FixtureInterface" />
-            <category class="Magento\Catalog\Test\Fixture\CatalogCategoryEntity" />
+            <category class="Magento\Catalog\Test\Fixture\CatalogCategory" />
             <catalogProductView class="Magento\Catalog\Test\Page\Product\CatalogProductView" />
             <catalogSearchResult class="Magento\CatalogSearch\Test\Page\CatalogsearchResult" />
         </require>
@@ -160,4 +158,113 @@
             <product class="Mtf\Fixture\FixtureInterface" />
         </require>
     </assertGroupedPriceOnProductPage>
+    <assertProductAttributeSaveMessage module="Magento_Catalog">
+        <severeness>high</severeness>
+        <require>
+            <attributeIndex class="Magento\Catalog\Test\Page\Adminhtml\CatalogProductAttributeIndex" />
+        </require>
+    </assertProductAttributeSaveMessage>
+    <assertProductAttributeInGrid module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeInGrid>
+    <assertAttributeOnAttributeForm module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertAttributeOnAttributeForm>
+    <assertProductAttributeOnProductForm module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeOnProductForm>
+    <assertProductAttributeIsRequired module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeIsRequired>
+    <assertAttributeSearchableByLabel module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertAttributeSearchableByLabel>
+    <assertProductAttributeIsUnique module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeIsUnique>
+    <assertProductAttributeDisplayingOnSearchForm module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeDisplayingOnSearchForm>
+    <assertProductAttributeIsComparable module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeIsComparable>
+    <assertProductAttributeDisplayingOnFrontend module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeDisplayingOnFrontend>
+    <assertProductAttributeIsHtmlAllowed module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeIsHtmlAllowed>
+    <assertProductAttributeIsFilterable module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeIsFilterable>
+    <assertProductAttributeIsFilterableInSearch module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeIsFilterableInSearch>
+    <assertAttributeOptionsOnProductForm module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertAttributeOptionsOnProductForm>
+    <assertProductAttributeIsUsedPromoRules module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeIsUsedPromoRules>
+    <assertProductAttributeUsedSortOnFrontend module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeUsedSortOnFrontend>
+    <assertProductAttributeIsGlobal module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertProductAttributeIsGlobal>
+    <assertCrossSellsProductsSection module="Magento_Catalog">
+        <severeness>middle</severeness>
+        <require>
+            <product1 class="Magento\Catalog\Test\Fixture\CatalogProductSimple" />
+            <product2 class="Magento\Catalog\Test\Fixture\CatalogProductSimple" />
+            <cmsIndex class="Magento\Cms\Test\Page\CmsIndex" />
+            <catalogCategoryView class="Magento\Catalog\Test\Page\Category\CatalogCategoryView" />
+            <catalogProductView class="Magento\Catalog\Test\Page\Product\CatalogProductView" />
+            <checkoutCart class="Magento\Checkout\Test\Page\CheckoutCart" />
+        </require>
+    </assertCrossSellsProductsSection>
+    <assertNoCrossSellsProductsSection module="Magento_Catalog">
+        <severeness>middle</severeness>
+    </assertNoCrossSellsProductsSection>
+    <assertRelatedProductsSection module="Magento_Catalog">
+        <severeness>middle</severeness>
+        <require>
+            <product1 class="Magento\Catalog\Test\Fixture\CatalogProductSimple" />
+            <product2 class="Magento\Catalog\Test\Fixture\CatalogProductSimple" />
+            <cmsIndex class="Magento\Cms\Test\Page\CmsIndex" />
+            <catalogCategoryView class="Magento\Catalog\Test\Page\Category\CatalogCategoryView" />
+            <catalogProductView class="Magento\Catalog\Test\Page\Product\CatalogProductView" />
+        </require>
+    </assertRelatedProductsSection>
+    <assertNoRelatedProductsSection module="Magento_Catalog">
+        <severeness>middle</severeness>
+    </assertNoRelatedProductsSection>
+    <assertUpSellsProductsSection module="Magento_Catalog">
+        <severeness>middle</severeness>
+        <require>
+            <product1 class="Magento\Catalog\Test\Fixture\CatalogProductSimple" />
+            <product2 class="Magento\Catalog\Test\Fixture\CatalogProductSimple" />
+            <cmsIndex class="Magento\Cms\Test\Page\CmsIndex" />
+            <catalogCategoryView class="Magento\Catalog\Test\Page\Category\CatalogCategoryView" />
+            <catalogProductView class="Magento\Catalog\Test\Page\Product\CatalogProductView" />
+        </require>
+    </assertUpSellsProductsSection>
+    <assertNoUpSellsProductsSection module="Magento_Catalog">
+        <severeness>middle</severeness>
+    </assertNoUpSellsProductsSection>
+    <assertCategorySaveMessage module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertCategorySaveMessage>
+    <assertCategoryForm module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertCategoryForm>
+    <assertCategoryPage module="Magento_Catalog">
+        <severeness>low</severeness>
+    </assertCategoryPage>
+    <assertAbsenceDeleteAttributeButton module="Magento_Catalog">
+        <severeness>high</severeness>
+        <require>
+            <attributeNew class="Magento\Catalog\Test\Page\Adminhtml\CatalogProductAttributeNew" />
+        </require>
+    </assertAbsenceDeleteAttributeButton>
 </constraint>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/fixture.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/fixture.xml
index 5b045a20921..38ac0903913 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/fixture.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/fixture.xml
@@ -168,11 +168,11 @@
             <input_prefix>product</input_prefix>
         </data_config>
     </catalogProductGrouped>
-    <catalogCategoryEntity module="Magento_Catalog">
+    <catalogCategory module="Magento_Catalog">
         <type>flat</type>
         <entity_type>catalog_category_entity</entity_type>
         <collection>Magento\Catalog\Model\Resource\Category\Collection</collection>
-    </catalogCategoryEntity>
+    </catalogCategory>
     <catalogProductVirtual module="Magento_Catalog">
         <type>eav</type>
         <entity_type>catalog_product</entity_type>
@@ -212,4 +212,12 @@
             <input_prefix>product</input_prefix>
         </data_config>
     </catalogProductVirtual>
+    <catalogProductAttribute module="Magento_Catalog">
+        <type>composite</type>
+        <entities>
+            <eav_attribute>eav_attribute</eav_attribute>
+            <catalog_eav_attribute>catalog_eav_attribute</catalog_eav_attribute>
+        </entities>
+        <collection>Magento\Catalog\Model\Resource\Attribute</collection>
+    </catalogProductAttribute>
 </fixture>
diff --git a/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/page.xml b/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/page.xml
index 6fb0c3f0a4d..a1436244cff 100644
--- a/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/page.xml
+++ b/dev/tests/functional/tests/app/Magento/Catalog/Test/etc/global/page.xml
@@ -49,4 +49,19 @@
         <area>category</area>
         <class>Magento\Catalog\Test\Page\Category\CatalogCategoryView</class>
     </catalogCategoryView>
+    <catalogProductAttributeIndex>
+        <mca>catalog/product_attribute/index</mca>
+        <area>adminhtml</area>
+        <class>Magento\Catalog\Test\Page\Adminhtml\CatalogProductAttributeIndex</class>
+    </catalogProductAttributeIndex>
+    <catalogProductAttributeNew>
+        <mca>catalog/product_attribute/new</mca>
+        <area>adminhtml</area>
+        <class>Magento\Catalog\Test\Page\Adminhtml\CatalogProductAttributeNew</class>
+    </catalogProductAttributeNew>
+    <catalogCategoryEdit>
+        <mca>catalog/category/edit</mca>
+        <area>adminhtml</area>
+        <class>Magento\Catalog\Test\Page\Adminhtml\CatalogCategoryEdit</class>
+    </catalogCategoryEdit>
 </page>
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Form/Advanced.php b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Form.php
similarity index 64%
rename from dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Form/Advanced.php
rename to dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Form.php
index 5848f2f2195..2582fb7a084 100644
--- a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Form/Advanced.php
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Form.php
@@ -22,18 +22,17 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-namespace Magento\CatalogSearch\Test\Block\Form;
+namespace Magento\CatalogSearch\Test\Block\Advanced;
 
-use Mtf\Fixture\FixtureInterface;
-use Mtf\Block\Form;
 use Mtf\Client\Element;
-use Mtf\Client\Element\Locator;
+use Mtf\Fixture\FixtureInterface;
+use Mtf\Block\Form as ParentForm;
 
 /**
- * Advanced form search block
- *
+ * Class Form
+ * Advanced search form
  */
-class Advanced extends Form
+class Form extends ParentForm
 {
     /**
      * Search button selector
@@ -42,8 +41,47 @@ class Advanced extends Form
      */
     protected $searchButtonSelector = '.action.search';
 
+    /**
+     * Field selector select tax class
+     *
+     * @var string
+     */
+    protected $taxClassSelector = '#tax_class_id';
+
+    /**
+     * Submit search form
+     *
+     * @return void
+     */
+    public function submit()
+    {
+        $this->_rootElement->find($this->searchButtonSelector)->click();
+    }
+
+    /**
+     * Fill the root form
+     *
+     * @param FixtureInterface $fixture
+     * @param Element|null $element
+     * @return $this
+     */
+    public function fill(FixtureInterface $fixture, Element $element = null)
+    {
+        // Prepare price data
+        $data = $fixture->getData();
+        $data = array_merge($data, $data['price']);
+        unset($data['price']);
+
+        // Mapping
+        $mapping = $this->dataMapping($data);
+        $this->_fill($mapping, $element);
+
+        return $this;
+    }
+
     /**
      * Fill form with custom fields
+     * (for End To End Tests)
      *
      * @param FixtureInterface $fixture
      * @param array $fields
@@ -56,12 +94,4 @@ class Advanced extends Form
         $mapping = $this->dataMapping($dataForMapping);
         $this->_fill($mapping, $element);
     }
-
-    /**
-     * Submit search form
-     */
-    public function submit()
-    {
-        $this->_rootElement->find($this->searchButtonSelector, Locator::SELECTOR_CSS)->click();
-    }
 }
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Form.xml b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Form.xml
new file mode 100644
index 00000000000..2e937e88532
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Form.xml
@@ -0,0 +1,51 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<mapping strict="0">
+    <fields>
+        <name>
+            <selector>#name</selector>
+        </name>
+        <sku>
+            <selector>#sku</selector>
+        </sku>
+        <description>
+            <selector>#description</selector>
+        </description>
+        <short_description>
+            <selector>#short_description</selector>
+        </short_description>
+        <price_from>
+            <selector>#price</selector>
+        </price_from>
+        <price_to>
+            <selector>#price_to</selector>
+        </price_to>
+        <tax_class_id>
+            <selector>#tax_class_id</selector>
+            <input>select</input>
+        </tax_class_id>
+    </fields>
+</mapping>
\ No newline at end of file
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Result.php b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Result.php
new file mode 100644
index 00000000000..01375b90998
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Block/Advanced/Result.php
@@ -0,0 +1,127 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\CatalogSearch\Test\Block\Advanced;
+
+use Mtf\Block\Block;
+use Mtf\Client\Element\Locator;
+
+/**
+ * Class Result
+ * Block for advanced search results
+ */
+class Result extends Block
+{
+    /**
+     * CSS selector for block 'Search summary'
+     *
+     * @var string
+     */
+    protected $searchSummary = '.search.summary';
+
+    /**
+     * XPath selector for block 'Search summary' item
+     *
+     * @var string
+     */
+    protected $searchSummaryItem = './/*[@class="item"][%d]';
+
+    /**
+     * XPath selector for block 'Search summary' items
+     *
+     * @var string
+     */
+    protected $searchSummaryItems = './/*[@class="items"][%d]';
+
+    /**
+     * XPath selector for block 'Messages'
+     *
+     * @var string
+     */
+    protected $messagesSelector = './/*[contains(@class,"message") and contains(.,"%s")]';
+
+    /**
+     * Checking the presence of the messages on the page
+     *
+     * @param string $text
+     * @return bool
+     */
+    public function isVisibleMessages($text)
+    {
+        return $this->_rootElement->find(sprintf($this->messagesSelector, $text), Locator::SELECTOR_XPATH)
+            ->isVisible();
+    }
+
+    /**
+     * Getting search data
+     *
+     * @return array
+     */
+    public function getSearchSummaryItems()
+    {
+        $result = [];
+        $index = 1;
+
+        $element = $this->_rootElement->find($this->searchSummary);
+        while ($element->find(sprintf($this->searchSummaryItems, $index), Locator::SELECTOR_XPATH)->isVisible()) {
+            $parentElement = $element->find(sprintf($this->searchSummaryItems, $index), Locator::SELECTOR_XPATH);
+            $childIndex = 1;
+            while ($parentElement->find(
+                sprintf($this->searchSummaryItem, $childIndex),
+                Locator::SELECTOR_XPATH
+            )->isVisible()) {
+                $result[] = $parentElement->find(
+                    sprintf($this->searchSummaryItem, $childIndex),
+                    Locator::SELECTOR_XPATH
+                )->getText();
+                ++$childIndex;
+            }
+            ++$index;
+        }
+
+        // Prepare data
+        foreach ($result as $key => $dataRow) {
+            $explodeData = explode(':', $dataRow);
+            $explodeData[1] = trim($explodeData[1]);
+            $explodeData[0] = str_replace(' ', '_', strtolower($explodeData[0]));
+            if ($explodeData[0] === 'price') {
+                $matches = [];
+                if (preg_match('#^(\d+)[^\d]+(\d+)$#umis', $explodeData[1], $matches)) { // range
+                    $result[$explodeData[0]][] = $matches[1];
+                    $result[$explodeData[0]][] = $matches[2];
+                } elseif (preg_match('#^[^\d]+(\d+)$#umis', $explodeData[1], $matches)) { // up to
+                    $result[$explodeData[0]][] = $matches[1];
+                } elseif (preg_match('#^(\d+)[^\d]+$#umis', $explodeData[1], $matches)) { // greater
+                    $result[$explodeData[0]][] = $matches[1];
+                }
+            } else {
+                $result[$explodeData[0]] = explode(',', $explodeData[1]);
+            }
+            $result[$explodeData[0]] = array_map('trim', $result[$explodeData[0]]);
+            unset($result[$key]);
+        }
+
+        return $result;
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Constraint/AssertAdvancedSearchProductsResult.php b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Constraint/AssertAdvancedSearchProductsResult.php
new file mode 100644
index 00000000000..2f7301cef9c
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Constraint/AssertAdvancedSearchProductsResult.php
@@ -0,0 +1,185 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\CatalogSearch\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\CatalogSearch\Test\Page\AdvancedResult;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+
+/**
+ * Class AssertAdvancedSearchProductsResult
+ */
+class AssertAdvancedSearchProductsResult extends AbstractConstraint
+{
+    /**
+     * Text for notice messages
+     */
+    const NOTICE_MESSAGE = "Don't see what you're looking for?";
+
+    /**
+     * Text for error messages
+     */
+    const ERROR_MESSAGE = 'No items were found using the following search criteria.';
+
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'high';
+
+    /**
+     * Search results page
+     *
+     * @var AdvancedResult
+     */
+    protected $resultPage;
+
+    /**
+     * Fixture placeholder data
+     *
+     * @var array
+     */
+    protected $placeholder = [
+        'tax_class_id' => 'tax_class',
+    ];
+
+    /**
+     * Assert that Advanced Search result page contains only product(s) according to requested from fixture
+     *
+     * @param array $products
+     * @param AdvancedResult $resultPage
+     * @param array $productsSearch
+     * @param CatalogProductSimple $productSearch
+     * @return void
+     */
+    public function processAssert(
+        array $products,
+        AdvancedResult $resultPage,
+        array $productsSearch,
+        CatalogProductSimple $productSearch
+    ) {
+        $this->resultPage = $resultPage;
+        $searchResult = [];
+        foreach ($products as $key => $value) {
+            if ($value === 'Yes') {
+                /** @var CatalogProductSimple $productsSearch [$key] */
+                $searchResult[$productsSearch[$key]->getSku()] = $productsSearch[$key];
+            }
+        }
+
+        $errors = $this->checkSearchData($searchResult, $productSearch);
+        foreach ($searchResult as $sku => $product) {
+            /** @var CatalogProductSimple $product */
+            $name = $product->getName();
+            $isProductVisible = $resultPage->getListProductBlock()->isProductVisible($product->getName());
+            while (!$isProductVisible && $resultPage->getToolbar()->nextPage()) {
+                $isProductVisible = $resultPage->getListProductBlock()->isProductVisible($product->getName());
+            }
+            if (!$isProductVisible) {
+                $errors[] = '- failed to find the product (SKU - "'
+                    . $sku . '", name - "' . $name . '") according to the search parameters';
+            }
+        }
+
+        \PHPUnit_Framework_Assert::assertTrue(
+            empty($errors),
+            "The following errors occurred:\n" . implode("\n", $errors)
+        );
+    }
+
+    /**
+     * Validation page displaying the search data
+     *
+     * @param array $searchResult
+     * @param CatalogProductSimple $productSearch
+     * @return array
+     */
+    protected function checkSearchData(array $searchResult, CatalogProductSimple $productSearch)
+    {
+        $searchBlock = $this->resultPage->getSearchResultBlock();
+        $errors = [];
+        $textMessage = self::NOTICE_MESSAGE;
+        if (empty($searchResult)) {
+            $textMessage = self::ERROR_MESSAGE;
+        }
+
+        if (!$searchBlock->isVisibleMessages($textMessage)) {
+            $errors[] = '- message does not match the search script';
+        }
+
+        $searchData = $searchBlock->getSearchSummaryItems();
+        $productData = $this->prepareFixtureData($productSearch);
+        foreach ($productData as $key => $data) {
+            if ($key === 'tax_class' && $data === ['All']) {
+                continue;
+            }
+            if (!isset($searchData[$key])) {
+                $errors[] = '- "' . $key . '" not found on the page';
+            } elseif ($searchData[$key] !== $data) {
+                $errors[] = '- "' . $key . '" value does not match the page';
+            }
+        }
+
+        return $errors;
+    }
+
+    /**
+     * Preparation of fixture data before comparing
+     *
+     * @param CatalogProductSimple $productSearch
+     * @return array
+     */
+    protected function prepareFixtureData(CatalogProductSimple $productSearch)
+    {
+        $compareData = [];
+        foreach ($productSearch->getData() as $key => $value) {
+            if ($key === 'price') {
+                if (isset($value['price_from'])) {
+                    $compareData[$key][] = $value['price_from'];
+                }
+                if (isset($value['price_to'])) {
+                    $compareData[$key][] = $value['price_to'];
+                }
+            } else {
+                $index = isset($this->placeholder[$key]) ? $this->placeholder[$key] : $key;
+                $compareData[$index][] = $value;
+            }
+        }
+        unset($compareData['url_key']);
+
+        return $compareData;
+    }
+
+    /**
+     * Returns a string representation of the object
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'All products are involved in the search were found successfully.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Constraint/AssertSuggestSearchingResult.php b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Constraint/AssertSuggestSearchingResult.php
index b59049d3cd9..25e5a6f37c3 100644
--- a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Constraint/AssertSuggestSearchingResult.php
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Constraint/AssertSuggestSearchingResult.php
@@ -56,8 +56,8 @@ class AssertSuggestSearchingResult extends AbstractConstraint
         $queryText = $catalogSearch->getQueryText();
         $searchBlock->fillSearch($queryText);
 
-        if ($amount = $catalogSearch->getNumResults()) {
-            $isVisible = $searchBlock->isSuggestSearchVisible($queryText, $amount);
+        if ($catalogSearch->hasData('num_results')) {
+            $isVisible = $searchBlock->isSuggestSearchVisible($queryText, $catalogSearch->getNumResults());
         } else {
             $isVisible = $searchBlock->isSuggestSearchVisible($queryText);
         }
@@ -69,7 +69,7 @@ class AssertSuggestSearchingResult extends AbstractConstraint
     }
 
     /**
-     * Returns a string representation of the object.
+     * Returns a string representation of the object
      *
      * @return string
      */
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedResult.php b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedResult.php
new file mode 100644
index 00000000000..30ffb06a116
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedResult.php
@@ -0,0 +1,71 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\CatalogSearch\Test\Page;
+
+/**
+ * Class AdvancedResult
+ */
+class AdvancedResult extends CatalogsearchResult
+{
+    const MCA = 'catalogsearch/advanced/result';
+
+    /**
+     * Custom constructor
+     *
+     * @return void
+     */
+    protected function _init()
+    {
+        $this->_blocks['searchResultBlock'] = [
+            'name' => 'searchResultBlock',
+            'class' => 'Magento\CatalogSearch\Test\Block\Advanced\Result',
+            'locator' => '.column.main',
+            'strategy' => 'css selector',
+        ];
+        $this->_blocks['toolbar'] = [
+            'name' => 'toolbar',
+            'class' => 'Magento\Catalog\Test\Block\Product\ProductList\Toolbar',
+            'locator' => '.column.main',
+            'strategy' => 'css selector',
+        ];
+        parent::_init();
+    }
+
+    /**
+     * @return \Magento\CatalogSearch\Test\Block\Advanced\Result
+     */
+    public function getSearchResultBlock()
+    {
+        return $this->getBlockInstance('searchResultBlock');
+    }
+
+    /**
+     * @return \Magento\Catalog\Test\Block\Product\ProductList\Toolbar
+     */
+    public function getToolbar()
+    {
+        return $this->getBlockInstance('toolbar');
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedResult.xml b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedResult.xml
new file mode 100644
index 00000000000..714f0403526
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedResult.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="catalogsearch/advanced/result" >
+    <block>
+        <name>searchResultBlock</name>
+        <class>Magento\CatalogSearch\Test\Block\Advanced\Result</class>
+        <locator>.column.main</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>toolbar</name>
+        <class>Magento\Catalog\Test\Block\Product\ProductList\Toolbar</class>
+        <locator>.column.main</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedSearch.php b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedSearch.php
new file mode 100644
index 00000000000..91eb6dc6be2
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedSearch.php
@@ -0,0 +1,52 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\CatalogSearch\Test\Page;
+
+use Mtf\Page\FrontendPage;
+
+/**
+ * Class AdvancedSearch
+ */
+class AdvancedSearch extends FrontendPage
+{
+    const MCA = 'catalogsearch/advanced';
+
+    protected $_blocks = [
+        'form' => [
+            'name' => 'form',
+            'class' => 'Magento\CatalogSearch\Test\Block\Advanced\Form',
+            'locator' => '.form.search.advanced',
+            'strategy' => 'css selector',
+        ],
+    ];
+
+    /**
+     * @return \Magento\CatalogSearch\Test\Block\Advanced\Form
+     */
+    public function getForm()
+    {
+        return $this->getBlockInstance('form');
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedSearch.xml b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedSearch.xml
new file mode 100644
index 00000000000..3ffb0005cc0
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/AdvancedSearch.xml
@@ -0,0 +1,33 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="catalogsearch/advanced" >
+    <block>
+        <name>form</name>
+        <class>Magento\CatalogSearch\Test\Block\Advanced\Form</class>
+        <locator>.form.search.advanced</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/CatalogsearchResult.php b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/CatalogsearchResult.php
index 996bed85661..d6f4bcd3b7f 100644
--- a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/CatalogsearchResult.php
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/CatalogsearchResult.php
@@ -24,46 +24,29 @@
 
 namespace Magento\CatalogSearch\Test\Page;
 
-use Mtf\Page\Page;
-use Mtf\Factory\Factory;
-use Mtf\Client\Element\Locator;
+use Mtf\Page\FrontendPage;
 
 /**
  * Class CatalogsearchResult
- * Search result page
- *
  */
-class CatalogsearchResult extends Page
+class CatalogsearchResult extends FrontendPage
 {
-    /**
-     * URL for home page
-     */
     const MCA = 'catalogsearch/result';
 
-    /**
-     * List of results of product search
-     *
-     * @var string
-     */
-    protected $listProductBlock = '.search.results';
-
-    /**
-     * Custom constructor
-     */
-    protected function _init()
-    {
-        $this->_url = $this->_url = $_ENV['app_frontend_url'] . self::MCA;
-    }
+    protected $_blocks = [
+        'listProductBlock' => [
+            'name' => 'listProductBlock',
+            'class' => 'Magento\Catalog\Test\Block\Product\ListProduct',
+            'locator' => '.search.results',
+            'strategy' => 'css selector',
+        ],
+    ];
 
     /**
-     * Get search results list block
-     *
      * @return \Magento\Catalog\Test\Block\Product\ListProduct
      */
     public function getListProductBlock()
     {
-        return Factory::getBlockFactory()->getMagentoCatalogProductListProduct(
-            $this->_browser->find($this->listProductBlock, Locator::SELECTOR_CSS)
-        );
+        return $this->getBlockInstance('listProductBlock');
     }
 }
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/CatalogsearchResult.xml b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/CatalogsearchResult.xml
new file mode 100644
index 00000000000..3ed22b1488a
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/CatalogsearchResult.xml
@@ -0,0 +1,33 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="catalogsearch/result" >
+    <block>
+        <name>listProductBlock</name>
+        <class>Magento\Catalog\Test\Block\Product\ListProduct</class>
+        <locator>.search.results</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchEntityTest.php b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchEntityTest.php
new file mode 100644
index 00000000000..01898df2aa9
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchEntityTest.php
@@ -0,0 +1,103 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\CatalogSearch\Test\TestCase;
+
+use Mtf\TestCase\Injectable;
+use Mtf\Fixture\FixtureFactory;
+use Magento\Cms\Test\Page\CmsIndex;
+use Magento\CatalogSearch\Test\Page\AdvancedSearch;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+
+/**
+ * Test Creation for AdvancedSearchEntity
+ *
+ * Test Flow:
+ * Preconditions:
+ * 1. Two specific simple product is created(unique sku,name,short/full description, tax class)
+ *
+ * Steps:
+ * 1. Navigate to Frontend
+ * 2. Click "Advanced Search"
+ * 3. Fill test data in to field(s)
+ * 4. Click "Search" button
+ * 5. Perform all asserts
+ *
+ * @group Search_Frontend_(MX)
+ * @ZephyrId MAGETWO-24729
+ */
+class AdvancedSearchEntityTest extends Injectable
+{
+    /**
+     * Prepare data
+     *
+     * @param FixtureFactory $fixtureFactory
+     * @return array
+     */
+    public function __prepare(FixtureFactory $fixtureFactory)
+    {
+        /** @var CatalogProductSimple $productSymbols */
+        $productSymbols = $fixtureFactory->createByCode(
+            'catalogProductSimple',
+            ['dataSet' => 'abc_dfj_simple_for_advancedsearch']
+        );
+        $productSymbols->persist();
+
+        /** @var CatalogProductSimple $productNumbers */
+        $productNumbers = $fixtureFactory->createByCode(
+            'catalogProductSimple',
+            ['dataSet' => 'adc_123_simple_for_advancedsearch']
+        );
+        $productNumbers->persist();
+
+        return [
+            'productsSearch' => [
+                'simple_1' => $productSymbols,
+                'simple_2' => $productNumbers
+            ]
+        ];
+    }
+
+    /**
+     * Run test creation for advanced search entity
+     *
+     * @param array $products
+     * @param CatalogProductSimple $productSearch
+     * @param CmsIndex $cmsIndex
+     * @param AdvancedSearch $searchPage
+     * @return void
+     */
+    public function testSearch(
+        array $products,
+        CatalogProductSimple $productSearch,
+        CmsIndex $cmsIndex,
+        AdvancedSearch $searchPage
+    ) {
+        $cmsIndex->open();
+        $cmsIndex->getSearchBlock()->clickAdvancedSearchButton();
+        $searchForm = $searchPage->getForm();
+        $searchForm->fill($productSearch);
+        $searchForm->submit();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchEntityTest/testSearch.csv b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchEntityTest/testSearch.csv
new file mode 100644
index 00000000000..20c355cc0c3
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchEntityTest/testSearch.csv
@@ -0,0 +1,14 @@
+"products/simple_1";"products/simple_2";"productSearch/data/name";"productSearch/data/sku";"productSearch/data/description";"productSearch/data/short_description";"productSearch/data/price/value/price_from";"productSearch/data/price/value/price_to";"productSearch/data/tax_class_id/dataSet";"constraint"
+"Yes";"-";"abc_dfj";"abc_dfj";"adc_Full";"abc_short";49;500;"Taxable Goods";"assertAdvancedSearchProductsResult"
+"Yes";"-";"abc";"-";"-";"-";"-";"-";"all";"assertAdvancedSearchProductsResult"
+"-";"Yes";"adc_123";"-";"-";"-";"-";"-";"all";"assertAdvancedSearchProductsResult"
+"Yes";"-";"-";"abc";"-";"-";"-";"-";"all";"assertAdvancedSearchProductsResult"
+"Yes";"-";"-";"abc_dfj";"-";"-";"-";"-";"all";"assertAdvancedSearchProductsResult"
+"Yes";"-";"-";"abc";"full";"-";"-";"-";"all";"assertAdvancedSearchProductsResult"
+"-";"Yes";"-";"-";"dfj_full";"-";"-";"-";"all";"assertAdvancedSearchProductsResult"
+"Yes";"-";"-";"-";"-";"short";"-";"-";"all";"assertAdvancedSearchProductsResult"
+"-";"-";"-";"-";"-";"dfj_short";"-";"-";"all";"assertAdvancedSearchProductsResult"
+"Yes";"Yes";"-";"-";"-";"-";"-";"-";"all";"assertAdvancedSearchProductsResult"
+"Yes";"-";"-";"-";"-";"-";50;50;"all";"assertAdvancedSearchProductsResult"
+"Yes";"Yes";"-";"-";"-";"-";"-";100;"all";"assertAdvancedSearchProductsResult"
+"Yes";"-";"abc_dfj";"abc_dfj";"adc_Full";"abc_short";49;50;"Taxable Goods";"assertAdvancedSearchProductsResult"
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchTest.php b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchTest.php
index 37f04387f75..f89c161590b 100644
--- a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchTest.php
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/TestCase/AdvancedSearchTest.php
@@ -54,7 +54,7 @@ class AdvancedSearchTest extends Functional
         //Steps
         $homePage->open();
         $homePage->getFooterBlock()->clickLink('Advanced Search');
-        $searchForm = $advancedSearchPage->getSearchForm();
+        $searchForm = $advancedSearchPage->getForm();
         $this->assertTrue($searchForm->isVisible(), '"Advanced Search" form is not opened');
         $searchForm->fillCustom($productFixture, array('name', 'sku'));
         $searchForm->submit();
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/etc/global/constraint.xml b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/etc/global/constraint.xml
index 123ca419303..378b643c476 100644
--- a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/etc/global/constraint.xml
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/etc/global/constraint.xml
@@ -31,4 +31,11 @@
             <catalogSearch class="Magento\CatalogSearch\Test\Fixture\CatalogSearchQuery" />
         </require>
     </assertSuggestSearchingResult>
+    <assertAdvancedSearchProductsResult module="Magento_CatalogSearch">
+        <severeness>high</severeness>
+        <require>
+            <resultPage class="Magento\CatalogSearch\Test\Page\Advanced\Result" />
+            <productSearch class="Magento\Catalog\Test\Fixture\CatalogProductSimple" />
+        </require>
+    </assertAdvancedSearchProductsResult>
 </constraint>
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/etc/global/page.xml b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/etc/global/page.xml
new file mode 100644
index 00000000000..5c581d37d87
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/etc/global/page.xml
@@ -0,0 +1,40 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page>
+    <catalogsearchResult>
+        <mca>catalogsearch/result</mca>
+        <class>Magento\CatalogSearch\Test\Page\CatalogsearchResult</class>
+    </catalogsearchResult>
+    <advanced>
+        <mca>catalogsearch/advanced</mca>
+        <class>Magento\CatalogSearch\Test\Page\Advanced</class>
+    </advanced>
+    <result>
+        <mca>catalogsearch/advanced/result</mca>
+        <area>advanced</area>
+        <class>Magento\CatalogSearch\Test\Page\Advanced\Result</class>
+    </result>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/DiscountCodes.php b/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/DiscountCodes.php
new file mode 100644
index 00000000000..32d2a61f841
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/DiscountCodes.php
@@ -0,0 +1,79 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Checkout\Test\Block\Cart;
+
+use Mtf\Block\Form;
+use Mtf\Client\Element;
+use Mtf\Client\Element\Locator;
+
+/**
+ * Class DiscountCodes
+ * Discount codes block
+ */
+class DiscountCodes extends Form
+{
+    /**
+     * Form wrapper selector
+     *
+     * @var string
+     */
+    protected $formWrapper = '.content';
+
+    /**
+     * Open discount codes form selector
+     *
+     * @var string
+     */
+    protected $openForm = '.title';
+
+    /**
+     * Fill discount code input selector
+     *
+     * @var string
+     */
+    protected $couponCode = '#coupon_code';
+
+    /**
+     * Click apply button selector
+     *
+     * @var string
+     */
+    protected $applyButton = '.action.apply';
+
+    /**
+     * Enter discount code and click apply button
+     *
+     * @param string $code
+     * @return void
+     */
+    public function applyCouponCode($code)
+    {
+        if (!$this->_rootElement->find($this->formWrapper)->isVisible()) {
+            $this->_rootElement->find($this->openForm, Locator::SELECTOR_CSS)->click();
+        }
+        $this->_rootElement->find($this->couponCode, Locator::SELECTOR_CSS)->setValue($code);
+        $this->_rootElement->find($this->applyButton, Locator::SELECTOR_CSS)->click();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Shipping.php b/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Shipping.php
new file mode 100644
index 00000000000..681148204d4
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Shipping.php
@@ -0,0 +1,149 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Checkout\Test\Block\Cart;
+
+use Mtf\Block\Form;
+use Mtf\Client\Element;
+use Mtf\Client\Element\Locator;
+use Magento\Customer\Test\Fixture\AddressInjectable;
+
+/**
+ * Class Shipping
+ * Cart shipping block
+ */
+class Shipping extends Form
+{
+    /**
+     * Form wrapper selector
+     *
+     * @var string
+     */
+    protected $formWrapper = '.content';
+
+    /**
+     * Open shipping form selector
+     *
+     * @var string
+     */
+    protected $openForm = '.title';
+
+    /**
+     * Get quote selector
+     *
+     * @var string
+     */
+    protected $getQuote = '.action.quote';
+
+    /**
+     * Update total selector
+     *
+     * @var string
+     */
+    protected $updateTotalSelector = '.action.update';
+
+    /**
+     * Selector to access the shipping carrier method
+     *
+     * @var string
+     */
+    protected $shippingMethod = '//span[text()="%s"]/following::*//*[contains(text(), "%s")]';
+
+    /**
+     * From with shipping available shipping methods
+     *
+     * @var string
+     */
+    protected $shippingMethodForm = '#co-shipping-method-form';
+
+    /**
+     * Open estimate shipping and tax form
+     *
+     * @return void
+     */
+    public function openEstimateShippingAndTax()
+    {
+        if (!$this->_rootElement->find($this->formWrapper)->isVisible()) {
+            $this->_rootElement->find($this->openForm)->click();
+        }
+    }
+
+    /**
+     * Click Get quote button
+     *
+     * @return void
+     */
+    public function clickGetQuote()
+    {
+        $this->_rootElement->find($this->getQuote)->click();
+    }
+
+    /**
+     * Select shipping method
+     *
+     * @param array $shipping
+     * @return void
+     */
+    public function selectShippingMethod(array $shipping)
+    {
+        $selector = sprintf($this->shippingMethod, $shipping['carrier'], $shipping['method']);
+        if (!$this->_rootElement->find($selector, Locator::SELECTOR_XPATH)->isVisible()) {
+            $this->openEstimateShippingAndTax();
+        }
+        $this->_rootElement->find($selector, Locator::SELECTOR_XPATH)->click();
+        $this->_rootElement->find($this->updateTotalSelector, Locator::SELECTOR_CSS)->click();
+    }
+
+    /**
+     * Fill shipping and tax form
+     *
+     * @param AddressInjectable $address
+     * @return void
+     */
+    public function fillEstimateShippingAndTax(AddressInjectable $address)
+    {
+        $this->openEstimateShippingAndTax();
+        $this->fill($address);
+        $this->clickGetQuote();
+    }
+
+    /**
+     * Determines if the specified shipping carrier/method is visible on the cart
+     *
+     * @param $carrier
+     * @param $method
+     * @return bool
+     */
+    public function isShippingCarrierMethodVisible($carrier, $method)
+    {
+        $shippingMethodForm = $this->_rootElement->find($this->shippingMethodForm);
+        $this->_rootElement->waitUntil(
+            function () use ($shippingMethodForm) {
+                return $shippingMethodForm->isVisible() ? true : null;
+            }
+        );
+        $selector = sprintf($this->shippingMethod, $carrier, $method);
+        return $this->_rootElement->find($selector, Locator::SELECTOR_XPATH)->isVisible();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Shipping.xml b/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Shipping.xml
new file mode 100644
index 00000000000..1fe157b1065
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Shipping.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<mapping strict="0">
+    <fields>
+        <country_id>
+            <input>select</input>
+        </country_id>
+        <region_id>
+            <input>select</input>
+        </region_id>
+        <region />
+        <postcode>
+            <selector>#postcode</selector>
+        </postcode>
+    </fields>
+</mapping>
diff --git a/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Totals.php b/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Totals.php
new file mode 100644
index 00000000000..64f5c607393
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Checkout/Test/Block/Cart/Totals.php
@@ -0,0 +1,147 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Checkout\Test\Block\Cart;
+
+use Mtf\Block\Block;
+use Mtf\Client\Element;
+use Mtf\Client\Element\Locator;
+
+/**
+ * Class Totals
+ * Cart totals block
+ */
+class Totals extends Block
+{
+    /**
+     * Grand total search mask
+     *
+     * @var string
+     */
+    protected $grandTotal = '//tr[normalize-space(td)="Grand Total"]//span';
+
+    /**
+     * Subtotal search mask
+     *
+     * @var string
+     */
+    protected $subtotal = '//tr[normalize-space(td)="Subtotal"]//span';
+
+    /**
+     * Tax search mask
+     *
+     * @var string
+     */
+    protected $tax = '//tr[normalize-space(td)="Tax"]//span';
+
+    /**
+     * Get shipping price selector
+     *
+     * @var string
+     */
+    protected $shippingPriceSelector = '.shipping.excl .price';
+
+    /**
+     * Get shipping price block selector
+     *
+     * @var string
+     */
+    protected $shippingPriceBlockSelector = '.totals.shipping.excl';
+
+    /**
+     * Get Grand Total Text
+     *
+     * @return array|string
+     */
+    public function getGrandTotal()
+    {
+        $grandTotal = $this->_rootElement->find($this->grandTotal, Locator::SELECTOR_XPATH)->getText();
+        return $this->escapeCurrency($grandTotal);
+    }
+
+    /**
+     * Get Tax text from Order Totals
+     *
+     * @return array|string
+     */
+    public function getTax()
+    {
+        $taxPrice = $this->_rootElement->find($this->tax, Locator::SELECTOR_XPATH)->getText();
+        return $this->escapeCurrency($taxPrice);
+    }
+
+    /**
+     * Check that Tax is visible
+     *
+     * @return bool
+     */
+    public function isTaxVisible()
+    {
+        return $this->_rootElement->find($this->tax, Locator::SELECTOR_XPATH)->isVisible();
+    }
+
+    /**
+     * Get Subtotal text
+     *
+     * @return string
+     */
+    public function getSubtotal()
+    {
+        $subTotal = $this->_rootElement->find($this->subtotal, Locator::SELECTOR_XPATH)->getText();
+        return $this->escapeCurrency($subTotal);
+    }
+
+    /**
+     * Method that escapes currency symbols
+     *
+     * @param string $price
+     * @return string
+     */
+    protected function escapeCurrency($price)
+    {
+        preg_match("/^\\D*\\s*([\\d,\\.]+)\\s*\\D*$/", $price, $matches);
+        return (isset($matches[1])) ? $matches[1] : null;
+    }
+
+    /**
+     * Get shipping price
+     *
+     * @return string
+     */
+    public function getShippingPrice()
+    {
+        $shippingPrice = $this->_rootElement->find($this->shippingPriceSelector, Locator::SELECTOR_CSS)->getText();
+        return $this->escapeCurrency($shippingPrice);
+    }
+
+    /**
+     * Is visible shipping price block
+     *
+     * @return bool
+     */
+    public function isVisibleShippingPriceBlock()
+    {
+        return  $this->_rootElement->find($this->shippingPriceBlockSelector, Locator::SELECTOR_CSS)->isVisible();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Checkout/Test/Page/CheckoutCart.php b/dev/tests/functional/tests/app/Magento/Checkout/Test/Page/CheckoutCart.php
index 93aaab1e0e2..9af22c8b0e7 100644
--- a/dev/tests/functional/tests/app/Magento/Checkout/Test/Page/CheckoutCart.php
+++ b/dev/tests/functional/tests/app/Magento/Checkout/Test/Page/CheckoutCart.php
@@ -24,110 +24,102 @@
 
 namespace Magento\Checkout\Test\Page;
 
-use Mtf\Page\Page;
-use Mtf\Factory\Factory;
-use Mtf\Client\Element\Locator;
-use Magento\Core\Test\Block\Messages;
-use Magento\Checkout\Test\Block;
-use Magento\Checkout\Test\Block\Cart;
-use Magento\Checkout\Test\Block\Cart\Totals;
-use Magento\Checkout\Test\Block\Cart\Shipping;
-use Magento\Catalog\Test\Block\Product\ProductList\Crosssell;
+use Mtf\Page\FrontendPage;
 
 /**
  * Class CheckoutCart
- * Checkout cart page
- *
  */
-class CheckoutCart extends Page
+class CheckoutCart extends FrontendPage
 {
     /**
      * URL for checkout cart page
      */
     const MCA = 'checkout/cart';
 
-    /**
-     * Cart shipping block
-     *
-     * @var string
-     */
-    protected $shippingBlock = '.block.shipping';
-
-    /**
-     * Cart totals block
-     *
-     * @var string
-     */
-    protected $totalsBlock = '#shopping-cart-totals-table';
-
-    /**
-     * Custom constructor
-     */
-    protected function _init()
-    {
-        $this->_url = $_ENV['app_frontend_url'] . self::MCA;
-    }
+    protected $_blocks = [
+        'cartBlock' => [
+            'name' => 'cartBlock',
+            'class' => 'Magento\Checkout\Test\Block\Cart',
+            'locator' => '//div[contains(@class, "cart container")]',
+            'strategy' => 'xpath',
+        ],
+        'messagesBlock' => [
+            'name' => 'messagesBlock',
+            'class' => 'Magento\Core\Test\Block\Messages',
+            'locator' => '.messages .messages',
+            'strategy' => 'css selector',
+        ],
+        'shippingBlock' => [
+            'name' => 'shippingBlock',
+            'class' => 'Magento\Checkout\Test\Block\Cart\Shipping',
+            'locator' => '.block.shipping',
+            'strategy' => 'css selector',
+        ],
+        'totalsBlock' => [
+            'name' => 'totalsBlock',
+            'class' => 'Magento\Checkout\Test\Block\Cart\Totals',
+            'locator' => '#shopping-cart-totals-table',
+            'strategy' => 'css selector',
+        ],
+        'crosssellBlock' => [
+            'name' => 'crosssellBlock',
+            'class' => 'Magento\Catalog\Test\Block\Product\ProductList\Crosssell',
+            'locator' => '//div[contains(@class, "block")][contains(@class, "crosssell")]',
+            'strategy' => 'xpath',
+        ],
+        'discountCodesBlock' => [
+            'name' => 'discountCodesBlock',
+            'class' => 'Magento\Checkout\Test\Block\Cart\DiscountCodes',
+            'locator' => '.block.discount',
+            'strategy' => 'css selector',
+        ],
+    ];
 
     /**
-     * Get shopping cart block
-     *
-     * @return Cart
+     * @return \Magento\Checkout\Test\Block\Cart
      */
     public function getCartBlock()
     {
-        return Factory::getBlockFactory()->getMagentoCheckoutCart(
-            $this->_browser->find('//div[contains(@class, "cart container")]', Locator::SELECTOR_XPATH)
-        );
+        return $this->getBlockInstance('cartBlock');
     }
 
     /**
-     * Get messages block
-     *
-     * @return Messages
+     * @return \Magento\Core\Test\Block\Messages
      */
     public function getMessagesBlock()
     {
-        return Factory::getBlockFactory()->getMagentoCoreMessages(
-            $this->_browser->find('.messages .messages', Locator::SELECTOR_CSS)
-        );
+        return $this->getBlockInstance('messagesBlock');
     }
 
     /**
-     * Get cart shipping block
-     *
-     * @return Shipping
+     * @return \Magento\Checkout\Test\Block\Cart\Shipping
      */
     public function getShippingBlock()
     {
-        return Factory::getBlockFactory()->getMagentoCheckoutCartShipping(
-            $this->_browser->find($this->shippingBlock, Locator::SELECTOR_CSS)
-        );
+        return $this->getBlockInstance('shippingBlock');
     }
 
     /**
-     * Get cart totals block
-     *
-     * @return Totals
+     * @return \Magento\Checkout\Test\Block\Cart\Totals
      */
     public function getTotalsBlock()
     {
-        return Factory::getBlockFactory()->getMagentoCheckoutCartTotals(
-            $this->_browser->find($this->totalsBlock, Locator::SELECTOR_CSS)
-        );
+        return $this->getBlockInstance('totalsBlock');
     }
 
     /**
-     * Retrieve cross-sells block
-     *
-     * @return Crosssell
+     * @return \Magento\Catalog\Test\Block\Product\ProductList\Crosssell
      */
     public function getCrosssellBlock()
     {
-        return Factory::getBlockFactory()->getMagentoCatalogProductProductListCrosssell(
-            $this->_browser->find(
-                '//div[contains(@class, "block")][contains(@class, "crosssell")]',
-                Locator::SELECTOR_XPATH
-            )
-        );
+        return $this->getBlockInstance('crosssellBlock');
+    }
+
+    /**
+     * @return \Magento\Checkout\Test\Block\Cart\DiscountCodes
+     */
+    public function getDiscountCodesBlock()
+    {
+        return $this->getBlockInstance('discountCodesBlock');
     }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Checkout/Test/Page/CheckoutCart.xml b/dev/tests/functional/tests/app/Magento/Checkout/Test/Page/CheckoutCart.xml
new file mode 100644
index 00000000000..82bbcbc16df
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Checkout/Test/Page/CheckoutCart.xml
@@ -0,0 +1,63 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="checkout/cart" >
+    <block>
+        <name>cartBlock</name>
+        <class>Magento\Checkout\Test\Block\Cart</class>
+        <locator>//div[contains(@class, "cart container")]</locator>
+        <strategy>xpath</strategy>
+    </block>
+    <block>
+        <name>messagesBlock</name>
+        <class>Magento\Core\Test\Block\Messages</class>
+        <locator>.messages .messages</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>shippingBlock</name>
+        <class>Magento\Checkout\Test\Block\Cart\Shipping</class>
+        <locator>.block.shipping</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>totalsBlock</name>
+        <class>Magento\Checkout\Test\Block\Cart\Totals</class>
+        <locator>#shopping-cart-totals-table</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>crosssellBlock</name>
+        <class>Magento\Catalog\Test\Block\Product\ProductList\Crosssell</class>
+        <locator>//div[contains(@class, "block")][contains(@class, "crosssell")]</locator>
+        <strategy>xpath</strategy>
+    </block>
+    <block>
+        <name>discountCodesBlock</name>
+        <class>Magento\Checkout\Test\Block\Cart\DiscountCodes</class>
+        <locator>.block.discount</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/Cms/Test/Page/CmsIndex.php b/dev/tests/functional/tests/app/Magento/Cms/Test/Page/CmsIndex.php
index bb5ac47b01c..6c5e2cf5df7 100644
--- a/dev/tests/functional/tests/app/Magento/Cms/Test/Page/CmsIndex.php
+++ b/dev/tests/functional/tests/app/Magento/Cms/Test/Page/CmsIndex.php
@@ -28,8 +28,6 @@ use Mtf\Page\FrontendPage;
 
 /**
  * Class CmsIndex
- *
- * @package Magento\Cms\Test\Page
  */
 class CmsIndex extends FrontendPage
 {
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/Edit/Tab/Super/Config.php b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/Edit/Tab/Super/Config.php
index 0a5f9f8a309..47300f19804 100644
--- a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/Edit/Tab/Super/Config.php
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/Edit/Tab/Super/Config.php
@@ -82,7 +82,7 @@ class Config extends Tab
      * @param string $attributeName
      * @return \Magento\ConfigurableProduct\Test\Block\Adminhtml\Product\Edit\Tab\Super\Attribute
      */
-    protected function getAttributeBlock($attributeName)
+    public function getAttributeBlock($attributeName)
     {
         $attributeSelector = sprintf($this->attribute, $attributeName);
         $this->waitForElementVisible($attributeSelector, Locator::SELECTOR_XPATH);
@@ -132,7 +132,9 @@ class Config extends Tab
         }
         $this->fillAttributeOptions($attributes);
         $this->generateVariations();
-        $this->fillVariationsMatrix($fields['variations-matrix']['value']);
+        if (isset($fields['variations-matrix']['value'])) {
+            $this->fillVariationsMatrix($fields['variations-matrix']['value']);
+        }
 
         return $this;
     }
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/ProductForm.php b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/ProductForm.php
index ea902660a7d..c6b42746512 100644
--- a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/ProductForm.php
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/ProductForm.php
@@ -32,24 +32,15 @@ use Mtf\Util\XmlConverter;
 use Mtf\Block\BlockFactory;
 use Mtf\Client\Element\Locator;
 use Mtf\Fixture\FixtureInterface;
-use Magento\Catalog\Test\Fixture\Product;
-use Magento\Catalog\Test\Fixture\Category;
-use Magento\Backend\Test\Block\Widget\Tab;
-use Magento\Backend\Test\Block\Widget\FormTabs;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
+use Magento\Catalog\Test\Block\Adminhtml\Product\ProductForm as ParentForm;
 
 /**
  * Class ProductForm
  * Product creation form
  */
-class ProductForm extends FormTabs
+class ProductForm extends ParentForm
 {
-    /**
-     * 'Save' split button
-     *
-     * @var string
-     */
-    protected $saveButton = '#save-split-button-button';
-
     /**
      * New attribute selector
      *
@@ -64,13 +55,6 @@ class ProductForm extends FormTabs
      */
     protected $newAttributeFrame = '#create_new_attribute_container';
 
-    /**
-     * Variations tab selector
-     *
-     * @var string
-     */
-    protected $variationsTab = '[data-ui-id="product-tabs-tab-content-super-config"] .title';
-
     /**
      * Variations tab selector
      *
@@ -78,20 +62,6 @@ class ProductForm extends FormTabs
      */
     protected $productDetailsTab = '#product_info_tabs_product-details';
 
-    /**
-     * Variations wrapper selector
-     *
-     * @var string
-     */
-    protected $variationsWrapper = '[data-ui-id="product-tabs-tab-content-super-config"]';
-
-    /**
-     * New variation set button selector
-     *
-     * @var string
-     */
-    protected $newVariationSet = '[data-ui-id="admin-product-edit-tab-super-config-grid-container-add-attribute"]';
-
     /**
      * Choose affected attribute set dialog popup window
      *
@@ -100,46 +70,18 @@ class ProductForm extends FormTabs
     protected $affectedAttributeSet = "//div[div/@data-id='affected-attribute-set-selector']";
 
     /**
-     * Category name selector
-     *
-     * @var string
-     */
-    protected $categoryName = '//*[contains(@class, "mage-suggest-choice")]/*[text()="%categoryName%"]';
-
-    /**
-     * 'Advanced Settings' tab
-     *
-     * @var string
-     */
-    protected $advancedSettings = '#ui-accordion-product_info_tabs-advanced-header-0[aria-selected="false"]';
-
-    /**
-     * Advanced tab list
+     * Variations tab selector
      *
      * @var string
      */
-    protected $advancedTabList = '#product_info_tabs-advanced[role="tablist"]';
+    protected $variationsTab = '[data-ui-id="product-tabs-tab-content-super-config"] .title';
 
     /**
-     * Advanced tab panel
+     * Variations wrapper selector
      *
      * @var string
      */
-    protected $advancedTabPanel = '[role="tablist"] [role="tabpanel"][aria-expanded="true"]:not("overflow")';
-
-    /**
-     * Category fixture
-     *
-     * @var Category
-     */
-    protected $category;
-
-    /**
-     * Client Browser
-     *
-     * @var Browser
-     */
-    protected $browser;
+    protected $variationsWrapper = '[data-ui-id="product-tabs-tab-content-super-config"]';
 
     /**
      * @param Element $element
@@ -187,10 +129,10 @@ class ProductForm extends FormTabs
     /**
      * Initialization categories before use in the form of
      *
-     * @param Category $category
+     * @param CatalogCategory $category
      * @return void
      */
-    public function setCategory(Category $category)
+    public function setCategory(CatalogCategory $category)
     {
         $this->category = $category;
     }
@@ -214,37 +156,7 @@ class ProductForm extends FormTabs
         }
         if ($fixture->getConfigurableOptions()) {
             $this->browser->switchToFrame();
-            $this->fillVariations($fixture->getConfigurableOptions());
-        }
-
-    }
-
-    /**
-     * Select category
-     *
-     * @param FixtureInterface $fixture
-     * @return void
-     */
-    protected function fillCategory(FixtureInterface $fixture)
-    {
-        // TODO should be removed after suggest widget implementation as typified element
-        $categoryName = $this->category
-            ? $this->category->getCategoryName()
-            : ($fixture->getCategoryName() ? $fixture->getCategoryName() : '');
-
-        if (!$categoryName) {
-            return;
-        }
-        $category = $this->_rootElement->find(
-            str_replace('%categoryName%', $categoryName, $this->categoryName),
-            Locator::SELECTOR_XPATH
-        );
-        if (!$category->isVisible()) {
-            $this->fillCategoryField(
-                $categoryName,
-                'category_ids-suggest',
-                '//*[@id="attribute-category_ids-container"]'
-            );
+            $this->variationsFill($fixture->getConfigurableOptions());
         }
     }
 
@@ -262,24 +174,6 @@ class ProductForm extends FormTabs
         }
     }
 
-    /**
-     * Save new category
-     *
-     * @param Product $fixture
-     */
-    public function addNewCategory(Product $fixture)
-    {
-        $this->openNewCategoryDialog();
-        $this->_rootElement->find('input#new_category_name', Locator::SELECTOR_CSS)
-            ->setValue($fixture->getNewCategoryName());
-
-        $this->clearCategorySelect();
-        $this->selectParentCategory();
-
-        $this->_rootElement->find('div.ui-dialog-buttonset button.action-create')->click();
-        $this->waitForElementNotVisible('div.ui-dialog-buttonset button.action-create');
-    }
-
     /**
      * Get variations block
      *
@@ -297,7 +191,7 @@ class ProductForm extends FormTabs
      *
      * @param array $variations
      */
-    public function fillVariations($variations)
+    public function variationsFill(array $variations)
     {
         $variationsBlock = $this->getVariationsBlock();
         $variationsBlock->fillAttributeOptions($variations);
@@ -321,102 +215,15 @@ class ProductForm extends FormTabs
     }
 
     /**
-     * Clear category field
-     */
-    public function clearCategorySelect()
-    {
-        $selectedCategory = 'li.mage-suggest-choice span.mage-suggest-choice-close';
-        if ($this->_rootElement->find($selectedCategory)->isVisible()) {
-            $this->_rootElement->find($selectedCategory)->click();
-        }
-    }
-
-    /**
-     * Select parent category for new one
-     */
-    protected function selectParentCategory()
-    {
-        // TODO should be removed after suggest widget implementation as typified element
-        $this->fillCategoryField(
-            'Default Category',
-            'new_category_parent-suggest',
-            '//*[@id="new_category_form_fieldset"]'
-        );
-    }
-
-    /**
-     * Fills select category field
+     * Find Attribute on Product page
      *
-     * @param string $name
-     * @param string $elementId
-     * @param string $parentLocation
+     * @param string $attributeName
+     * @return bool
      */
-    protected function fillCategoryField($name, $elementId, $parentLocation)
+    public function findAttribute($attributeName)
     {
-        // TODO should be removed after suggest widget implementation as typified element
-        $this->_rootElement->find($elementId, Locator::SELECTOR_ID)->setValue($name);
-        //*[@id="attribute-category_ids-container"]  //*[@id="new_category_form_fieldset"]
-        $categoryListLocation = $parentLocation . '//div[@class="mage-suggest-dropdown"]'; //
-        $this->waitForElementVisible($categoryListLocation, Locator::SELECTOR_XPATH);
-        $categoryLocation = $parentLocation . '//li[contains(@data-suggest-option, \'"label":"' . $name . '",\')]//a';
-        $this->_rootElement->find($categoryLocation, Locator::SELECTOR_XPATH)->click();
-    }
-
-    /**
-     * Open new category dialog
-     */
-    protected function openNewCategoryDialog()
-    {
-        $this->_rootElement->find('#add_category_button', Locator::SELECTOR_CSS)->click();
-        $this->waitForElementVisible('input#new_category_name');
-    }
-
-    /**
-     * Open tab
-     *
-     * @param string $tabName
-     * @return Tab|bool
-     */
-    public function openTab($tabName)
-    {
-        $rootElement = $this->_rootElement;
-        $selector = $this->tabs[$tabName]['selector'];
-        $strategy = isset($this->tabs[$tabName]['strategy'])
-            ? $this->tabs[$tabName]['strategy']
-            : Locator::SELECTOR_CSS;
-        $advancedTabList = $this->advancedTabList;
-        $tab = $this->_rootElement->find($selector, $strategy);
-        $advancedSettings = $this->_rootElement->find($this->advancedSettings);
-
-        // Wait until all tabs will load
-        $this->_rootElement->waitUntil(
-            function () use ($rootElement, $advancedTabList) {
-                return $rootElement->find($advancedTabList)->isVisible();
-            }
-        );
-
-        if ($tab->isVisible()) {
-            $tab->click();
-        } elseif ($advancedSettings->isVisible()) {
-            $advancedSettings->click();
-            // Wait for open tab animation
-            $tabPanel = $this->advancedTabPanel;
-            $this->_rootElement->waitUntil(
-                function () use ($rootElement, $tabPanel) {
-                    return $rootElement->find($tabPanel)->isVisible();
-                }
-            );
-            // Wait until needed tab will appear
-            $this->_rootElement->waitUntil(
-                function () use ($rootElement, $selector, $strategy) {
-                    return $rootElement->find($selector, $strategy)->isVisible();
-                }
-            );
-            $tab->click();
-        } else {
-            return false;
-        }
+        $this->openTab('product-details');
 
-        return $this;
+        return $this->getVariationsBlock()->getAttributeBlock($attributeName)->isVisible();
     }
 }
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/ProductForm.xml b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/ProductForm.xml
index 16b9d6dfdc9..1362f3e17af 100644
--- a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/ProductForm.xml
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Block/Adminhtml/Product/ProductForm.xml
@@ -45,18 +45,6 @@
             </quantity_and_stock_status>
         </fields>
     </product-details>
-    <websites>
-        <class>\Magento\Backend\Test\Block\Widget\Tab</class>
-        <selector>#product_info_tabs_websites</selector>
-        <strategy>css selector</strategy>
-        <wrapper>product</wrapper>
-        <fields>
-            <product_website_1>
-                <selector>[name='product[website_ids][]']</selector>
-                <input>checkbox</input>
-            </product_website_1>
-        </fields>
-    </websites>
     <advanced-pricing>
         <class>\Magento\Catalog\Test\Block\Adminhtml\Product\Edit\AdvancedPricingTab</class>
         <selector>#product_info_tabs_advanced-pricing</selector>
@@ -74,65 +62,9 @@
             </tier_price>
         </fields>
     </advanced-pricing>
-    <advanced-inventory>
-        <class>\Magento\Backend\Test\Block\Widget\Tab</class>
-        <selector>#product_info_tabs_advanced-inventory</selector>
-        <strategy>css selector</strategy>
-        <wrapper>product[stock_data]</wrapper>
-        <fields>
-            <inventory_manage_stock>
-                <selector>[name='product[stock_data][manage_stock]']</selector>
-                <input>select</input>
-            </inventory_manage_stock>
-            <inventory_qty>
-                <selector>[name='product[stock_data][qty]']</selector>
-            </inventory_qty>
-        </fields>
-    </advanced-inventory>
-    <autosettings>
-        <class>\Magento\Backend\Test\Block\Widget\Tab</class>
-        <selector>#product_info_tabs_autosettings</selector>
-        <strategy>css selector</strategy>
-        <wrapper>product</wrapper>
-        <fields>
-            <visibility>
-                <input>select</input>
-            </visibility>
-        </fields>
-    </autosettings>
     <variations>
         <class>\Magento\ConfigurableProduct\Test\Block\Adminhtml\Product\Edit\Tab\Super\Config</class>
         <selector>#product_info_tabs_product-details</selector>
         <strategy>css selector</strategy>
     </variations>
-    <grouped-product>
-        <class>\Magento\Catalog\Test\Block\Product\Grouped\AssociatedProducts</class>
-        <selector>#product_info_tabs_product-details</selector>
-        <strategy>css selector</strategy>
-    </grouped-product>
-    <customer-options>
-        <class>\Magento\Catalog\Test\Block\Adminhtml\Product\Edit\CustomOptionsTab</class>
-        <selector>#product_info_tabs_customer_options</selector>
-        <strategy>css selector</strategy>
-        <fields>
-            <custom_options>
-                <input>select</input>
-            </custom_options>
-        </fields>
-    </customer-options>
-    <related-products>
-        <class>\Magento\Catalog\Test\Block\Adminhtml\Product\Edit\Tab\Related</class>
-        <selector>#product_info_tabs_related</selector>
-        <strategy>css selector</strategy>
-    </related-products>
-    <upsells>
-        <class>\Magento\Catalog\Test\Block\Adminhtml\Product\Edit\Tab\Upsell</class>
-        <selector>#product_info_tabs_upsell</selector>
-        <strategy>css selector</strategy>
-    </upsells>
-    <crosssells>
-        <class>\Magento\Catalog\Test\Block\Adminhtml\Product\Edit\Tab\Crosssell</class>
-        <selector>#product_info_tabs_crosssell</selector>
-        <strategy>css selector</strategy>
-    </crosssells>
 </tabs>
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertConfigurableInCategory.php b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertConfigurableInCategory.php
index 52dabb996b5..03c60d74f23 100644
--- a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertConfigurableInCategory.php
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertConfigurableInCategory.php
@@ -25,9 +25,9 @@
 namespace Magento\ConfigurableProduct\Test\Constraint;
 
 use Mtf\Constraint\AbstractConstraint;
-use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
 use Magento\Cms\Test\Page\CmsIndex;
-use Magento\Catalog\Test\Fixture\Category;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
+use Magento\Catalog\Test\Page\Category\CatalogCategoryView;
 use Magento\ConfigurableProduct\Test\Fixture\CatalogProductConfigurable;
 
 /**
@@ -48,18 +48,18 @@ class AssertConfigurableInCategory extends AbstractConstraint
      * @param CatalogCategoryView $catalogCategoryView
      * @param CmsIndex $cmsIndex
      * @param CatalogProductConfigurable $configurable
-     * @param Category $category
+     * @param CatalogCategory $category
      * @return void
      */
     public function processAssert(
         CatalogCategoryView $catalogCategoryView,
         CmsIndex $cmsIndex,
         CatalogProductConfigurable $configurable,
-        Category $category
+        CatalogCategory $category
     ) {
         //Open category view page
         $cmsIndex->open();
-        $cmsIndex->getTopmenu()->selectCategoryByName($category->getCategoryName());
+        $cmsIndex->getTopmenu()->selectCategoryByName($category->getName());
 
         //process asserts
         $this->assertPrice($configurable, $catalogCategoryView);
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertConfigurableInGrid.php b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertConfigurableInGrid.php
index a127b5bfe5f..0bd4f7ffd02 100644
--- a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertConfigurableInGrid.php
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertConfigurableInGrid.php
@@ -43,17 +43,17 @@ class AssertConfigurableInGrid extends AbstractConstraint
     /**
      * Assert product availability in products grid
      *
-     * @param CatalogProductConfigurable $product
+     * @param CatalogProductConfigurable $configurable
      * @param CatalogProductIndex $productPageGrid
      * @return void
      */
-    public function processAssert(CatalogProductConfigurable $product, CatalogProductIndex $productPageGrid)
+    public function processAssert(CatalogProductConfigurable $configurable, CatalogProductIndex $productPageGrid)
     {
-        $filter = ['sku' => $product->getSku()];
+        $filter = ['sku' => $configurable->getSku()];
         $productPageGrid->open();
         \PHPUnit_Framework_Assert::assertTrue(
             $productPageGrid->getProductGrid()->isRowVisible($filter),
-            'Product with sku \'' . $product->getSku() . '\' is absent in Products grid.'
+            'Product with sku \'' . $configurable->getSku() . '\' is absent in Products grid.'
         );
     }
 
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertProductAttributeIsConfigurable.php b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertProductAttributeIsConfigurable.php
new file mode 100644
index 00000000000..6f110172b7a
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Constraint/AssertProductAttributeIsConfigurable.php
@@ -0,0 +1,106 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\ConfigurableProduct\Test\Constraint;
+
+use Mtf\Fixture\FixtureFactory;
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Catalog\Test\Fixture\CatalogProductAttribute;
+use Magento\Catalog\Test\Page\Adminhtml\CatalogProductIndex;
+use Magento\ConfigurableProduct\Test\Fixture\CatalogProductConfigurable;
+use Magento\ConfigurableProduct\Test\Page\Adminhtml\CatalogProductNew;
+
+/**
+ * Class AssertProductAttributeIsConfigurable
+ */
+class AssertProductAttributeIsConfigurable extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'high';
+
+    /**
+     * Attribute frontend label
+     *
+     * @var string
+     */
+    protected $attributeFrontendLabel;
+
+    /**
+     * Assert check whether the attribute is used to create a configurable products
+     *
+     * @param CatalogProductAttribute $productAttribute
+     * @param CatalogProductIndex $productGrid
+     * @param FixtureFactory $fixtureFactory
+     * @param CatalogProductNew $newProductPage
+     */
+    public function processAssert
+    (
+        CatalogProductAttribute $productAttribute,
+        CatalogProductIndex $productGrid,
+        FixtureFactory $fixtureFactory,
+        CatalogProductNew $newProductPage
+    ) {
+        $this->attributeFrontendLabel = $productAttribute->getFrontendLabel();
+        $productGrid->open();
+        $productGrid->getProductBlock()->addProduct('configurable');
+
+        $productConfigurable = $fixtureFactory->createByCode(
+            'catalogProductConfigurable',
+            [
+                'dataSet' => 'default',
+                'data' => [
+                    'configurable_attributes_data' => [
+                        'value' => [
+                            'label' => [
+                                'value' => $this->attributeFrontendLabel
+                            ]
+                        ]
+                    ]
+                ],
+            ]
+        );
+
+        $productBlockForm = $newProductPage->getForm();
+        $productBlockForm->fill($productConfigurable);
+
+        \PHPUnit_Framework_Assert::assertTrue(
+            $newProductPage->getForm()->findAttribute($this->attributeFrontendLabel),
+            "Product Attribute is absent on Product page."
+        );
+    }
+
+    /**
+     * Attribute '$this->attributeFrontendLabel' present on the product page in variations section
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return "$this->attributeFrontendLabel attribute present on the product page in variations section";
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Fixture/CatalogProductConfigurable.php b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Fixture/CatalogProductConfigurable.php
index 3edae23277f..4c36a7a6884 100644
--- a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Fixture/CatalogProductConfigurable.php
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Fixture/CatalogProductConfigurable.php
@@ -29,6 +29,7 @@ use Mtf\Handler\HandlerFactory;
 use Mtf\Fixture\FixtureFactory;
 use Mtf\Fixture\InjectableFixture;
 use Mtf\Repository\RepositoryFactory;
+use Mtf\System\Event\EventManagerInterface;
 
 /**
  * Class CatalogProductConfigurable
@@ -36,6 +37,15 @@ use Mtf\Repository\RepositoryFactory;
  */
 class CatalogProductConfigurable extends InjectableFixture
 {
+    /**
+     * @var string
+     */
+    protected $repositoryClass = 'Magento\ConfigurableProduct\Test\Repository\CatalogProductConfigurable';
+
+    /**
+     * @var string
+     */
+    protected $handlerInterface = 'Magento\ConfigurableProduct\Test\Handler\CatalogProductConfigurable\CatalogProductConfigurableInterface';
     /**
      * Constructor
      *
@@ -44,6 +54,7 @@ class CatalogProductConfigurable extends InjectableFixture
      * @param RepositoryFactory $repositoryFactory
      * @param FixtureFactory $fixtureFactory
      * @param HandlerFactory $handlerFactory
+     * @param EventManagerInterface $eventManager
      * @param array $data
      * @param string $dataSet
      * @param bool $persist
@@ -53,6 +64,7 @@ class CatalogProductConfigurable extends InjectableFixture
         RepositoryFactory $repositoryFactory,
         FixtureFactory $fixtureFactory,
         HandlerFactory $handlerFactory,
+        EventManagerInterface $eventManager,
         array $data = [],
         $dataSet = '',
         $persist = false
@@ -62,6 +74,7 @@ class CatalogProductConfigurable extends InjectableFixture
             $repositoryFactory,
             $fixtureFactory,
             $handlerFactory,
+            $eventManager,
             $data,
             $dataSet,
             $persist
@@ -80,14 +93,12 @@ class CatalogProductConfigurable extends InjectableFixture
     ];
 
     protected $defaultDataSet = [
-        'enable_googlecheckout' => null,
-        'msrp_display_actual_price_type' => null,
-        'msrp_enabled' => null,
-        'options_container' => null,
-        'quantity_and_stock_status' => null,
-        'status' => null,
-        'tax_class_id' => null,
-        'visibility' => null,
+        'type_id' => 'configurable',
+        'attribute_set_id' => 'Default',
+        'name' => 'Configurable Product %isolation%',
+        'sku' => 'sku_configurable_product_%isolation%',
+        'price' => ['value' => 100.00],
+        'weight' => 1,
     ];
 
     protected $category_ids = [
@@ -457,6 +468,8 @@ class CatalogProductConfigurable extends InjectableFixture
         'is_required' => '0',
         'default_value' => 'Taxable Goods',
         'input' => 'select',
+        'group' => 'product-details',
+        'source' => 'Magento\Catalog\Test\Fixture\CatalogProductSimple\TaxClass',
     ];
 
     protected $thumbnail = [
@@ -499,6 +512,7 @@ class CatalogProductConfigurable extends InjectableFixture
         'is_required' => '0',
         'default_value' => '',
         'input' => 'text',
+        'group' => 'autosettings',
     ];
 
     protected $url_path = [
@@ -545,7 +559,7 @@ class CatalogProductConfigurable extends InjectableFixture
     protected $attribute_set_name = [
         'attribute_code' => 'attribute_set_name',
         'backend_type' => 'virtual',
-        'group' => 'product-details'
+        'group' => 'variations'
     ];
 
     protected $qty = [
@@ -580,6 +594,22 @@ class CatalogProductConfigurable extends InjectableFixture
         'source' => 'Magento\ConfigurableProduct\Test\Fixture\CatalogProductConfigurable\AttributeOptions',
     ];
 
+    protected $configurable_attributes_data = [
+        'attribute_code' => 'configurable_options_data',
+        'backend_type' => 'virtual',
+        'is_required' => '0',
+        'input' => 'variations',
+        'group' => 'variations',
+    ];
+
+    protected $variations_matrix = [
+        'attribute_code' => 'variations_matrix',
+        'backend_type' => 'virtual',
+        'is_required' => '0',
+        'input' => 'variations',
+        'group' => 'variations',
+    ];
+
     public function getCategoryIds()
     {
         return $this->getData('category_ids');
diff --git a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/Advanced.php b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Page/Adminhtml/CatalogProductNew.php
similarity index 56%
rename from dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/Advanced.php
rename to dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Page/Adminhtml/CatalogProductNew.php
index 19d66263698..42e4d61f360 100644
--- a/dev/tests/functional/tests/app/Magento/CatalogSearch/Test/Page/Advanced.php
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Page/Adminhtml/CatalogProductNew.php
@@ -22,47 +22,36 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-namespace Magento\CatalogSearch\Test\Page;
+namespace Magento\ConfigurableProduct\Test\Page\Adminhtml;
 
-use Mtf\Page\Page;
-use Mtf\Factory\Factory;
-use Mtf\Client\Element\Locator;
+use Mtf\Page\BackendPage;
+use Magento\Catalog\Test\Page\Adminhtml\CatalogProductNew as ParentCatalogProductNew;
 
 /**
- * Advanced search page
- *
+ * Class CatalogProductNew
  */
-class Advanced extends Page
+class CatalogProductNew extends ParentCatalogProductNew
 {
-    /**
-     * URL for search advanced page
-     */
-    const MCA = 'catalogsearch/advanced';
-
-    /**
-     * Advanced search form
-     *
-     * @var string
-     */
-    protected $searchForm = '.form.search.advanced';
-
+    const MCA = 'catalog/product_configurable/new';
     /**
      * Custom constructor
      */
     protected function _init()
     {
-        $this->_url = $_ENV['app_frontend_url'] . self::MCA;
+        $this->_blocks['form'] = [
+            'name' => 'form',
+            'class' => 'Magento\ConfigurableProduct\Test\Block\Adminhtml\Product\ProductForm',
+            'locator' => '[id="page:main-container"]',
+            'strategy' => 'css selector',
+        ];
+        $this->_url = $_ENV['app_backend_url'] . static::MCA;
     }
 
     /**
-     * Get search block form
-     *
-     * @return \Magento\CatalogSearch\Test\Block\Form\Advanced
+     * @return \Magento\ConfigurableProduct\Test\Block\Adminhtml\Product\ProductForm
      */
-    public function getSearchForm()
+    public function getForm()
     {
-        return Factory::getBlockFactory()->getMagentoCatalogSearchFormAdvanced(
-            $this->_browser->find($this->searchForm, Locator::SELECTOR_CSS)
-        );
+        return $this->getBlockInstance('form');
     }
 }
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Page/Adminhtml/CatalogProductNew.xml b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Page/Adminhtml/CatalogProductNew.xml
new file mode 100644
index 00000000000..f15ec3f9760
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Page/Adminhtml/CatalogProductNew.xml
@@ -0,0 +1,33 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="catalog/product_configurable/new">
+    <block>
+        <name>form</name>
+        <class>Magento\ConfigurableProduct\Test\Block\Adminhtml\Product\ProductForm</class>
+        <locator>[id="page:main-container"]</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Repository/CatalogProductConfigurable.php b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Repository/CatalogProductConfigurable.php
new file mode 100644
index 00000000000..10ed462496d
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/Repository/CatalogProductConfigurable.php
@@ -0,0 +1,44 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\ConfigurableProduct\Test\Repository;
+
+use Mtf\Repository\AbstractRepository;
+
+/**
+ * Class CatalogProductSimple
+ * Data for creation Catalog Product Configurable
+ */
+class CatalogProductConfigurable extends AbstractRepository
+{
+    public function __construct(array $defaultConfig = [], array $defaultData = [])
+    {
+        $this->_data['default'] = [
+            'name' => 'Configurable Product %isolation%',
+            'sku' => 'sku_configurable_product_%isolation%',
+            'price' => ['value' => 100.00],
+            'weight' => 1
+        ];
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/TestCase/Product/CreateConfigurableEntityTest.php b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/TestCase/Product/CreateConfigurableEntityTest.php
index 0562cf4341d..acaad382330 100644
--- a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/TestCase/Product/CreateConfigurableEntityTest.php
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/TestCase/Product/CreateConfigurableEntityTest.php
@@ -25,7 +25,7 @@
 namespace Magento\ConfigurableProduct\Test\TestCase\Product;
 
 use Mtf\TestCase\Injectable;
-use Magento\Catalog\Test\Fixture\Category;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 use Magento\Catalog\Test\Page\Adminhtml\CatalogProductNew;
 use Magento\Catalog\Test\Page\Adminhtml\CatalogProductIndex;
 use Magento\ConfigurableProduct\Test\Fixture\CatalogProductConfigurable;
@@ -48,7 +48,7 @@ class CreateConfigurableEntityTest extends Injectable
     /**
      * Category fixture
      *
-     * @var Category
+     * @var CatalogCategory
      */
     protected $category;
 
@@ -67,10 +67,10 @@ class CreateConfigurableEntityTest extends Injectable
     protected $newProductPage;
 
     /**
-     * @param Category $category
+     * @param CatalogCategory $category
      * @return array
      */
-    public function __prepare(Category $category)
+    public function __prepare(CatalogCategory $category)
     {
         $category->persist();
 
@@ -80,12 +80,12 @@ class CreateConfigurableEntityTest extends Injectable
     }
 
     /**
-     * @param Category $category
+     * @param CatalogCategory $category
      * @param CatalogProductIndex $productPageGrid
      * @param CatalogProductNew $newProductPage
      */
     public function __inject(
-        Category $category,
+        CatalogCategory $category,
         CatalogProductIndex $productPageGrid,
         CatalogProductNew $newProductPage
     ) {
@@ -98,10 +98,10 @@ class CreateConfigurableEntityTest extends Injectable
      * Run create configurable product test
      *
      * @param CatalogProductConfigurable $configurable
-     * @param Category $category
+     * @param CatalogCategory $category
      * @return void
      */
-    public function testCreate(CatalogProductConfigurable $configurable, Category $category)
+    public function testCreate(CatalogProductConfigurable $configurable, CatalogCategory $category)
     {
         // Steps
         $this->productPageGrid->open();
diff --git a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/etc/global/constraint.xml b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/etc/global/constraint.xml
index 3bf2ef45279..a377726694e 100644
--- a/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/etc/global/constraint.xml
+++ b/dev/tests/functional/tests/app/Magento/ConfigurableProduct/Test/etc/global/constraint.xml
@@ -55,4 +55,12 @@
             <checkoutCart class="Magento\Checkout\Test\Page\CheckoutCart" />
         </require>
     </assertConfigurableInCart>
+    <assertProductAttributeIsConfigurable module="Magento_ConfigurableProduct">
+        <severeness>high</severeness>
+        <require>
+            <productAttribute class="Magento\Catalog\Test\Fixture\CatalogAttributeEntity" />
+            <productGrid class="Magento\Catalog\Test\Page\Adminhtml\CatalogProductIndex" />
+            <newProductPage class="Magento\Catalog\Test\Page\Adminhtml\CatalogProductNew" />
+        </require>
+    </assertProductAttributeIsConfigurable>
 </constraint>
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/Form.php b/dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/CustomerForm.php
similarity index 98%
rename from dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/Form.php
rename to dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/CustomerForm.php
index 4b0170c6b5d..477e44bbd5c 100644
--- a/dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/Form.php
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/CustomerForm.php
@@ -29,11 +29,10 @@ use Magento\Backend\Test\Block\Widget\FormTabs;
 use Mtf\Fixture\InjectableFixture;
 
 /**
- * Class Form
+ * Class CustomerForm
  * Form for creation of the customer
- *
  */
-class Form extends FormTabs
+class CustomerForm extends FormTabs
 {
     /**
      * Fill Customer forms on tabs by customer, addresses data
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/Form.xml b/dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/CustomerForm.xml
similarity index 100%
rename from dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/Form.xml
rename to dev/tests/functional/tests/app/Magento/Customer/Test/Block/Adminhtml/Edit/CustomerForm.xml
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/Constraint/AssertCustomerFailRegisterMessage.php b/dev/tests/functional/tests/app/Magento/Customer/Test/Constraint/AssertCustomerFailRegisterMessage.php
new file mode 100644
index 00000000000..db80b50777e
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/Constraint/AssertCustomerFailRegisterMessage.php
@@ -0,0 +1,66 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Customer\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Customer\Test\Page\CustomerAccountCreate;
+
+/**
+ * Class AssertCustomerFailRegisterMessage
+ */
+class AssertCustomerFailRegisterMessage extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'high';
+
+    /**
+     * Assert that error message is displayed on "Create New Customer Account" page(frontend)
+     *
+     * @param CustomerAccountCreate $registerPage
+     * @return void
+     */
+    public function processAssert(CustomerAccountCreate $registerPage)
+    {
+        $errorMessage = $registerPage->getMessagesBlock()->getErrorMessages();
+        \PHPUnit_Framework_Assert::assertNotEmpty(
+            $errorMessage,
+            'No error message is displayed.'
+        );
+    }
+
+    /**
+     * Text error message is displayed
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Assert that error message is displayed.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/Fixture/AddressInjectable.php b/dev/tests/functional/tests/app/Magento/Customer/Test/Fixture/AddressInjectable.php
index 6ea904a389f..4a0a8a94968 100644
--- a/dev/tests/functional/tests/app/Magento/Customer/Test/Fixture/AddressInjectable.php
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/Fixture/AddressInjectable.php
@@ -28,7 +28,6 @@ use Mtf\Fixture\InjectableFixture;
 
 /**
  * Class AddressInjectable
- *
  */
 class AddressInjectable extends InjectableFixture
 {
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexEdit.php b/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexEdit.php
index a07e1c6b015..6f56600ae44 100644
--- a/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexEdit.php
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexEdit.php
@@ -55,7 +55,7 @@ class CustomerIndexEdit extends BackendPage
         ],
         'customerForm' => [
             'name' => 'customerForm',
-            'class' => 'Magento\Customer\Test\Block\Adminhtml\Edit\Form',
+            'class' => 'Magento\Customer\Test\Block\Adminhtml\Edit\CustomerForm',
             'locator' => '[id="page:main-container"]',
             'strategy' => 'css selector',
         ],
@@ -86,7 +86,7 @@ class CustomerIndexEdit extends BackendPage
     }
 
     /**
-     * @return \Magento\Customer\Test\Block\Adminhtml\Edit\Form
+     * @return \Magento\Customer\Test\Block\Adminhtml\Edit\CustomerForm
      */
     public function getCustomerForm()
     {
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexEdit.xml b/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexEdit.xml
index 7b5d547bb7d..be40c5cda32 100644
--- a/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexEdit.xml
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexEdit.xml
@@ -44,7 +44,7 @@
     </block>
     <block>
         <name>customerForm</name>
-        <class>Magento\Customer\Test\Block\Adminhtml\Edit\Form</class>
+        <class>Magento\Customer\Test\Block\Adminhtml\Edit\CustomerForm</class>
         <locator>[id="page:main-container"]</locator>
         <strategy>css selector</strategy>
     </block>
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexNew.php b/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexNew.php
index a7df02c0d72..5bae25d11c8 100644
--- a/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexNew.php
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexNew.php
@@ -49,7 +49,7 @@ class CustomerIndexNew extends BackendPage
         ],
         'customerForm' => [
             'name' => 'customerForm',
-            'class' => 'Magento\Customer\Test\Block\Adminhtml\Edit\Form',
+            'class' => 'Magento\Customer\Test\Block\Adminhtml\Edit\CustomerForm',
             'locator' => '[id="page:main-container"]',
             'strategy' => 'css selector',
         ],
@@ -72,7 +72,7 @@ class CustomerIndexNew extends BackendPage
     }
 
     /**
-     * @return \Magento\Customer\Test\Block\Adminhtml\Edit\Form
+     * @return \Magento\Customer\Test\Block\Adminhtml\Edit\CustomerForm
      */
     public function getCustomerForm()
     {
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexNew.xml b/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexNew.xml
index b6962468a8f..c1589cce1a3 100644
--- a/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexNew.xml
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/Page/Adminhtml/CustomerIndexNew.xml
@@ -38,7 +38,7 @@
     </block>
     <block>
         <name>customerForm</name>
-        <class>Magento\Customer\Test\Block\Adminhtml\Edit\Form</class>
+        <class>Magento\Customer\Test\Block\Adminhtml\Edit\CustomerForm</class>
         <locator>[id="page:main-container"]</locator>
         <strategy>css selector</strategy>
     </block>
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/Page/CustomerAccountCreate.php b/dev/tests/functional/tests/app/Magento/Customer/Test/Page/CustomerAccountCreate.php
index 767b36ee762..6d1420a5b24 100644
--- a/dev/tests/functional/tests/app/Magento/Customer/Test/Page/CustomerAccountCreate.php
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/Page/CustomerAccountCreate.php
@@ -28,7 +28,6 @@ use Mtf\Page\FrontendPage;
 
 /**
  * Class CustomerAccountCreate
- *
  */
 class CustomerAccountCreate extends FrontendPage
 {
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/TestCase/CreateExistingCustomerFrontendEntity.php b/dev/tests/functional/tests/app/Magento/Customer/Test/TestCase/CreateExistingCustomerFrontendEntity.php
new file mode 100644
index 00000000000..3fdf493623b
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/TestCase/CreateExistingCustomerFrontendEntity.php
@@ -0,0 +1,120 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Customer\Test\TestCase;
+
+use Magento\Customer\Test\Fixture\CustomerInjectable;
+use Magento\Customer\Test\Page\CustomerAccountCreate;
+use Magento\Cms\Test\Page\CmsIndex;
+use Magento\Customer\Test\Page\CustomerAccountLogout;
+use Mtf\TestCase\Injectable;
+
+/**
+ * Test Creation for CreateExistingCustomerFrontendEntity
+ *
+ * Test Flow:
+ * Preconditions:
+ *  1.Customer is created
+ * Steps:
+ * 1. Go to frontend.
+ * 2. Click Register link.
+ * 3. Fill registry form.
+ * 4. Click 'Create account' button.
+ * 5. Perform assertions.
+ *
+ * @group Customer_Account_(CS)
+ * @ZephyrId MAGETWO-23545
+ */
+class CreateExistingCustomerFrontendEntity extends Injectable
+{
+    /**
+     * Page CustomerAccountCreate
+     *
+     * @var CustomerAccountCreate
+     */
+    protected $customerAccountCreate;
+
+    /**
+     * Page CustomerAccountLogout
+     *
+     * @var CustomerAccountLogout
+     */
+    protected $customerAccountLogout;
+
+    /**
+     * Page CmsIndex
+     *
+     * @var CmsIndex
+     */
+    protected $cmsIndex;
+
+    /**
+     * Injection data
+     *
+     * @param CustomerAccountCreate $customerAccountCreate
+     * @param CustomerAccountLogout $customerAccountLogout
+     * @param CmsIndex $cmsIndex
+     * @param CustomerInjectable $customer
+     * @return array
+     */
+    public function __inject(
+        CustomerAccountCreate $customerAccountCreate,
+        CustomerAccountLogout $customerAccountLogout,
+        CmsIndex $cmsIndex,
+        CustomerInjectable $customer
+    ) {
+        $this->customerAccountLogout = $customerAccountLogout;
+        $this->customerAccountCreate = $customerAccountCreate;
+        $this->cmsIndex = $cmsIndex;
+        //Precondition
+        $customer->persist();
+        return [
+            'customer' => $customer,
+        ];
+    }
+
+    /**
+     * Create Existing Customer account on frontend
+     *
+     * @param CustomerInjectable $customer
+     * @return void
+     */
+    public function testCreateExistingCustomer(CustomerInjectable $customer)
+    {
+        //Steps
+        $this->cmsIndex->open();
+        $this->cmsIndex->getLinksBlock()->openLink('Register');
+        $this->customerAccountCreate->getRegisterForm()->registerCustomer($customer);
+    }
+
+    /**
+     * Logout customer from frontend account
+     *
+     * @return void
+     */
+    public function tearDown()
+    {
+        $this->customerAccountLogout->open();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/TestCase/CreateExistingCustomerFrontendEntity/testCreateExistingCustomer.csv b/dev/tests/functional/tests/app/Magento/Customer/Test/TestCase/CreateExistingCustomerFrontendEntity/testCreateExistingCustomer.csv
new file mode 100644
index 00000000000..2ef3cf9e336
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/TestCase/CreateExistingCustomerFrontendEntity/testCreateExistingCustomer.csv
@@ -0,0 +1,2 @@
+"constraint"
+"assertCustomerFailRegisterMessage"
\ No newline at end of file
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/etc/curl/di.xml b/dev/tests/functional/tests/app/Magento/Customer/Test/etc/curl/di.xml
index 00a17f9778b..4ea2277356e 100644
--- a/dev/tests/functional/tests/app/Magento/Customer/Test/etc/curl/di.xml
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/etc/curl/di.xml
@@ -23,8 +23,6 @@
  * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
  */
 -->
-<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
-        xsi:noNamespaceSchemaLocation="../../../../../../../../../../lib/Magento/Framework/ObjectManager/etc/config.xsd">
-    <preference for="Magento\Customer\Test\Handler\CustomerInjectable\CustomerInjectableInterface"
-                type="\Magento\Customer\Test\Handler\CustomerInjectable\Curl"/>
+<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../../../../lib/internal/Magento/Framework/ObjectManager/etc/config.xsd">
+    <preference for="Magento\Customer\Test\Handler\CustomerInjectable\CustomerInjectableInterface" type="\Magento\Customer\Test\Handler\CustomerInjectable\Curl"/>
 </config>
diff --git a/dev/tests/functional/tests/app/Magento/Customer/Test/etc/global/constraint.xml b/dev/tests/functional/tests/app/Magento/Customer/Test/etc/global/constraint.xml
index 7e62e8457fe..aa20c921c46 100644
--- a/dev/tests/functional/tests/app/Magento/Customer/Test/etc/global/constraint.xml
+++ b/dev/tests/functional/tests/app/Magento/Customer/Test/etc/global/constraint.xml
@@ -87,4 +87,10 @@
     <assertCustomerGroupNotInGrid module="Magento_Customer">
         <severeness>low</severeness>
     </assertCustomerGroupNotInGrid>
+    <assertCustomerFailRegisterMessage module="Magento_Customer">
+        <severeness>high</severeness>
+        <require>
+            <registerPage class="Magento\Customer\Test\Page\CustomerAccountCreate" />
+        </require>
+    </assertCustomerFailRegisterMessage>
 </constraint>
diff --git a/dev/tests/functional/tests/app/Magento/Downloadable/Test/Block/Adminhtml/Product/Form.xml b/dev/tests/functional/tests/app/Magento/Downloadable/Test/Block/Adminhtml/Product/ProductForm.xml
similarity index 100%
rename from dev/tests/functional/tests/app/Magento/Downloadable/Test/Block/Adminhtml/Product/Form.xml
rename to dev/tests/functional/tests/app/Magento/Downloadable/Test/Block/Adminhtml/Product/ProductForm.xml
diff --git a/dev/tests/functional/tests/app/Magento/Downloadable/Test/Constraint/AssertDownloadableProductForm.php b/dev/tests/functional/tests/app/Magento/Downloadable/Test/Constraint/AssertDownloadableProductForm.php
index 55fc50f6b2e..905b881fd5f 100644
--- a/dev/tests/functional/tests/app/Magento/Downloadable/Test/Constraint/AssertDownloadableProductForm.php
+++ b/dev/tests/functional/tests/app/Magento/Downloadable/Test/Constraint/AssertDownloadableProductForm.php
@@ -25,9 +25,9 @@
 namespace Magento\Downloadable\Test\Constraint;
 
 use Magento\Catalog\Test\Constraint\AssertProductForm;
-use Mtf\Fixture\InjectableFixture;
+use Mtf\Fixture\FixtureInterface;
 use Magento\Catalog\Test\Page\Adminhtml\CatalogProductIndex;
-use Magento\Catalog\Test\Page\Adminhtml\CatalogProductNew;
+use Magento\Catalog\Test\Page\Adminhtml\CatalogProductEdit;
 
 /**
  * Class AssertDownloadableProductForm
@@ -44,15 +44,15 @@ class AssertDownloadableProductForm extends AssertProductForm
     /**
      * Assert that downloadable product data on edit page equals to passed from fixture
      *
-     * @param InjectableFixture $product
+     * @param FixtureInterface $product
      * @param CatalogProductIndex $productGrid
-     * @param CatalogProductNew $productPage
+     * @param CatalogProductEdit $productPage
      * @return void
      */
     public function processAssert(
-        InjectableFixture $product,
+        FixtureInterface $product,
         CatalogProductIndex $productGrid,
-        CatalogProductNew $productPage
+        CatalogProductEdit $productPage
     ) {
         $filter = ['sku' => $product->getData('sku')];
         $productGrid->open()->getProductGrid()->searchAndOpen($filter);
diff --git a/dev/tests/functional/tests/app/Magento/Downloadable/Test/Fixture/CatalogProductDownloadable.php b/dev/tests/functional/tests/app/Magento/Downloadable/Test/Fixture/CatalogProductDownloadable.php
index 1b990416827..e54ea692f01 100644
--- a/dev/tests/functional/tests/app/Magento/Downloadable/Test/Fixture/CatalogProductDownloadable.php
+++ b/dev/tests/functional/tests/app/Magento/Downloadable/Test/Fixture/CatalogProductDownloadable.php
@@ -29,6 +29,7 @@ use Mtf\System\Config;
 use Mtf\Handler\HandlerFactory;
 use Mtf\Fixture\FixtureFactory;
 use Mtf\Repository\RepositoryFactory;
+use Mtf\System\Event\EventManagerInterface;
 
 /**
  * Class CatalogProductDownloadable
@@ -54,6 +55,7 @@ class CatalogProductDownloadable extends InjectableFixture
      * @param RepositoryFactory $repositoryFactory
      * @param FixtureFactory $fixtureFactory
      * @param HandlerFactory $handlerFactory
+     * @param EventManagerInterface $eventManager
      * @param array $data
      * @param string $dataSet
      * @param bool $persist
@@ -63,6 +65,7 @@ class CatalogProductDownloadable extends InjectableFixture
         RepositoryFactory $repositoryFactory,
         FixtureFactory $fixtureFactory,
         HandlerFactory $handlerFactory,
+        EventManagerInterface $eventManager,
         array $data = [],
         $dataSet = '',
         $persist = false
@@ -72,6 +75,7 @@ class CatalogProductDownloadable extends InjectableFixture
             $repositoryFactory,
             $fixtureFactory,
             $handlerFactory,
+            $eventManager,
             $data,
             $dataSet,
             $persist
@@ -95,7 +99,7 @@ class CatalogProductDownloadable extends InjectableFixture
         'name' => 'DownloadableProduct_%isolation%',
         'sku' => 'DownloadableProduct_%isolation%',
         'price' => '100',
-        'tax_class' => 'Taxable Goods',
+        'tax_class_id' => ['dataSet' => 'Taxable Goods'],
         'description' => 'This is description for downloadable product',
         'short_description' => 'This is short description for downloadable product',
         'quantity_and_stock_status_qty' => '1',
@@ -542,7 +546,8 @@ class CatalogProductDownloadable extends InjectableFixture
         'is_required' => '0',
         'default_value' => '2',
         'input' => 'select',
-        'group' => 'product-details'
+        'group' => 'product-details',
+        'source' => 'Magento\Catalog\Test\Fixture\CatalogProductSimple\TaxClass',
     ];
 
     protected $thumbnail = [
diff --git a/dev/tests/functional/tests/app/Magento/Downloadable/Test/TestCase/CreateDownloadableProductEntityTest.php b/dev/tests/functional/tests/app/Magento/Downloadable/Test/TestCase/CreateDownloadableProductEntityTest.php
index a63ccb7a773..12b34392d64 100644
--- a/dev/tests/functional/tests/app/Magento/Downloadable/Test/TestCase/CreateDownloadableProductEntityTest.php
+++ b/dev/tests/functional/tests/app/Magento/Downloadable/Test/TestCase/CreateDownloadableProductEntityTest.php
@@ -25,7 +25,7 @@
 namespace Magento\Downloadable\Test\TestCase;
 
 use Mtf\TestCase\Injectable;
-use Magento\Catalog\Test\Fixture\CatalogCategoryEntity;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 use Magento\Catalog\Test\Page\Adminhtml\CatalogProductNew;
 use Magento\Catalog\Test\Page\Adminhtml\CatalogProductIndex;
 use Magento\Downloadable\Test\Fixture\CatalogProductDownloadable;
@@ -50,7 +50,7 @@ class CreateDownloadableProductEntityTest extends Injectable
     /**
      * Fixture category
      *
-     * @var CatalogCategoryEntity
+     * @var CatalogCategory
      */
     protected $category;
 
@@ -71,10 +71,10 @@ class CreateDownloadableProductEntityTest extends Injectable
     /**
      * Persist category
      *
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @return array
      */
-    public function __prepare(CatalogCategoryEntity $category)
+    public function __prepare(CatalogCategory $category)
     {
         $category->persist();
         return [
@@ -85,12 +85,12 @@ class CreateDownloadableProductEntityTest extends Injectable
     /**
      * Filling objects of the class
      *
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @param CatalogProductIndex $catalogProductIndexNewPage
      * @param CatalogProductNew $catalogProductNewPage
      */
     public function __inject(
-        CatalogCategoryEntity $category,
+        CatalogCategory $category,
         CatalogProductIndex $catalogProductIndexNewPage,
         CatalogProductNew $catalogProductNewPage
     ) {
@@ -103,9 +103,9 @@ class CreateDownloadableProductEntityTest extends Injectable
      * Test create downloadable product
      *
      * @param CatalogProductDownloadable $product
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      */
-    public function testCreateDownloadableProduct(CatalogProductDownloadable $product, CatalogCategoryEntity $category)
+    public function testCreateDownloadableProduct(CatalogProductDownloadable $product, CatalogCategory $category)
     {
         $this->catalogProductIndex->open();
         $this->catalogProductIndex->getProductBlock()->addProduct('downloadable');
diff --git a/dev/tests/functional/tests/app/Magento/Downloadable/Test/TestCase/CreateDownloadableProductEntityTest/testCreateDownloadableProduct.csv b/dev/tests/functional/tests/app/Magento/Downloadable/Test/TestCase/CreateDownloadableProductEntityTest/testCreateDownloadableProduct.csv
index bd7bc3f326b..347e99671fc 100644
--- a/dev/tests/functional/tests/app/Magento/Downloadable/Test/TestCase/CreateDownloadableProductEntityTest/testCreateDownloadableProduct.csv
+++ b/dev/tests/functional/tests/app/Magento/Downloadable/Test/TestCase/CreateDownloadableProductEntityTest/testCreateDownloadableProduct.csv
@@ -1,4 +1,4 @@
-product/data/name;product/data/sku;product/data/price;product/data/tax_class;product/data/qty;product/data/quantity_and_stock_status;product/data/is_virtual;product/data/category;product/data/description;product/data/short_description;product/data/inventory_manage_stock;product/data/inventory_qty;product/data/stock_data_use_config_min_qty;product/data/stock_data_min_qty;product/data/downloadable_sample/preset;product/data/downloadable_links/preset;product/data/custom_options/preset;product/data/special_price;product/data/group_price/preset;product/data/tier_price/preset;constraint
+product/data/name;product/data/sku;product/data/price;product/data/tax_class_id/dataSet;product/data/qty;product/data/quantity_and_stock_status;product/data/is_virtual;product/data/category;product/data/description;product/data/short_description;product/data/inventory_manage_stock;product/data/inventory_qty;product/data/stock_data_use_config_min_qty;product/data/stock_data_min_qty;product/data/downloadable_sample/preset;product/data/downloadable_links/preset;product/data/custom_options/preset;product/data/special_price;product/data/group_price/preset;product/data/tier_price/preset;constraint
 DownloadableProduct_%isolation%;DownloadableProduct_%isolation%;100;Taxable Goods;1;In Stock;Yes;Default Category;-;-;-;-;-;-;-;default;-;-;-;-;assertProductSaveMessage, assertProductInGrid, assertDownloadableProductForm, assertProductVisibleInCategory, assertProductPage, assertProductInStock
 DownloadableProduct_%isolation%;DownloadableProduct_%isolation%;1;Taxable Goods;10;In Stock;Yes;category %isolation%;-;-;-;-;-;-;default;default;-;-;-;-;assertProductSaveMessage, assertProductInGrid, assertDownloadableProductForm, assertProductVisibleInCategory, assertDownloadableSamplesData, assertDownloadableLinks
 DownloadableProduct_%isolation%;DownloadableProduct_%isolation%;33;Taxable Goods;10;In Stock;Yes;category %isolation%;-;-;-;-;-;-;-;default;default;-;-;-;assertProductSaveMessage, assertDownloadableProductForm, assertCustomOptionsOnProductPage, assertProductVisibleInCategory, assertProductPage, assertDownloadableLinks
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Edit/RatingForm.php b/dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Edit/RatingForm.php
new file mode 100644
index 00000000000..40e11199e62
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Edit/RatingForm.php
@@ -0,0 +1,36 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\Block\Adminhtml\Rating\Edit;
+
+use Magento\Backend\Test\Block\Widget\FormTabs;
+
+/**
+ * Class RatingForm
+ * Product rating form on backend product rating page
+ */
+class RatingForm extends FormTabs
+{
+    //
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Edit/RatingForm.xml b/dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Edit/RatingForm.xml
new file mode 100644
index 00000000000..5d97be275e6
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Edit/RatingForm.xml
@@ -0,0 +1,41 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<tabs>
+    <rating_information>
+        <class>\Magento\Backend\Test\Block\Widget\Tab</class>
+        <selector>#rating_tabs_form_section</selector>
+        <strategy>css selector</strategy>
+        <fields>
+            <stores>
+                <selector>[name="stores[]"]</selector>
+                <input>multiselectgrouplist</input>
+            </stores>
+            <is_active>
+                <input>checkbox</input>
+            </is_active>
+        </fields>
+    </rating_information>
+</tabs>
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Grid.php b/dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Grid.php
new file mode 100644
index 00000000000..06ea8c643f5
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Block/Adminhtml/Rating/Grid.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\Block\Adminhtml\Rating;
+
+use Magento\Backend\Test\Block\Widget\Grid as AbstractGrid;
+
+/**
+ * Class RatingGrid
+ * Backend product rating grid
+ */
+class Grid extends AbstractGrid
+{
+    /**
+     * Locator value for rating code column
+     *
+     * @var string
+     */
+    protected $editLink = 'td[data-column="rating_code"]';
+
+    /**
+     * Filters array mapping
+     *
+     * @var array
+     */
+    protected $filters = [
+        'rating_code' => [
+            'selector' => '.filter [name="rating_code"]',
+        ],
+        'is_active' => [
+            'selector' => '.filter [name="is_active"]',
+            'input' => 'select',
+        ],
+    ];
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Block/Form.php b/dev/tests/functional/tests/app/Magento/Review/Test/Block/Form.php
index bea96e86ee7..1d92a000c30 100644
--- a/dev/tests/functional/tests/app/Magento/Review/Test/Block/Form.php
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Block/Form.php
@@ -24,13 +24,14 @@
 
 namespace Magento\Review\Test\Block;
 
+use Magento\Review\Test\Fixture\Rating;
 use Mtf\Block\Form as BlockForm;
 use Mtf\Client\Element;
 use Mtf\Client\Element\Locator;
 
 /**
+ * Class Form
  * Review form
- *
  */
 class Form extends BlockForm
 {
@@ -48,6 +49,13 @@ class Form extends BlockForm
      */
     protected $submitButton = '.action.submit';
 
+    /**
+     * Single product rating selector
+     *
+     * @var string
+     */
+    protected $rating = './/*[@id="%s_rating_label"]/..[contains(@class,"rating")]';
+
     /**
      * Submit review form
      */
@@ -65,4 +73,26 @@ class Form extends BlockForm
     {
         return $this->_rootElement->find($this->legendSelector);
     }
+
+    /**
+     * Check rating element is visible
+     *
+     * @param Rating $rating
+     * @return bool
+     */
+    public function isVisibleRating(Rating $rating)
+    {
+        return $this->getRating($rating)->isVisible();
+    }
+
+    /**
+     * Get single product rating
+     *
+     * @param Rating $rating
+     * @return Element
+     */
+    protected function getRating(Rating $rating)
+    {
+        return $this->_rootElement->find(sprintf($this->rating, $rating->getRatingCode()), Locator::SELECTOR_XPATH);
+    }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingInGrid.php b/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingInGrid.php
new file mode 100644
index 00000000000..c21132f3c50
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingInGrid.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductRatingInGrid
+ */
+class AssertProductRatingInGrid extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'middle';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingInProductPage.php b/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingInProductPage.php
new file mode 100644
index 00000000000..e54c451aab2
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingInProductPage.php
@@ -0,0 +1,77 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\Constraint;
+
+use Magento\Catalog\Test\Page\Product\CatalogProductView;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Review\Test\Fixture\Rating;
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductRatingInProductPage
+ */
+class AssertProductRatingInProductPage extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'middle';
+
+    /**
+     * Assert that product rating is displayed on frontend on product review
+     *
+     * @param CatalogProductView $catalogProductView
+     * @param CatalogProductSimple $product
+     * @param Rating $productRating
+     * @return void
+     */
+    public function processAssert(
+        CatalogProductView $catalogProductView,
+        CatalogProductSimple $product,
+        Rating $productRating
+    ) {
+        $catalogProductView->init($product);
+        $catalogProductView->open();
+        $catalogProductView->getReviewSummaryBlock()->getAddReviewLink()->click();
+
+        $reviewForm = $catalogProductView->getReviewFormBlock();
+        \PHPUnit_Framework_Assert::assertTrue(
+            $reviewForm->isVisibleRating($productRating),
+            'Product rating "' . $productRating->getRatingCode() . '" is not displayed.'
+        );
+    }
+
+    /**
+     * Text success product rating is displayed
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Product rating is displayed.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingNotInProductPage.php b/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingNotInProductPage.php
new file mode 100644
index 00000000000..d19aea6948b
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingNotInProductPage.php
@@ -0,0 +1,77 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\Constraint;
+
+use Magento\Catalog\Test\Page\Product\CatalogProductView;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Review\Test\Fixture\Rating;
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductRatingNotInProductPage
+ */
+class AssertProductRatingNotInProductPage extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'middle';
+
+    /**
+     * Assert that product rating is not displayed on frontend on product review
+     *
+     * @param CatalogProductView $catalogProductView
+     * @param CatalogProductSimple $product
+     * @param Rating $productRating
+     * @return void
+     */
+    public function processAssert(
+        CatalogProductView $catalogProductView,
+        CatalogProductSimple $product,
+        Rating $productRating
+    ) {
+        $catalogProductView->init($product);
+        $catalogProductView->open();
+        $catalogProductView->getReviewSummaryBlock()->getAddReviewLink()->click();
+
+        $reviewForm = $catalogProductView->getReviewFormBlock();
+        \PHPUnit_Framework_Assert::assertFalse(
+            $reviewForm->isVisibleRating($productRating),
+            'Product rating "' . $productRating->getRatingCode() . '" is displayed.'
+        );
+    }
+
+    /**
+     * Text success product rating is not displayed
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Product rating is not displayed.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingSuccessSaveMessage.php b/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingSuccessSaveMessage.php
new file mode 100644
index 00000000000..e59be5ffc50
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Constraint/AssertProductRatingSuccessSaveMessage.php
@@ -0,0 +1,71 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\Constraint;
+
+use Magento\Review\Test\Page\Adminhtml\RatingIndex;
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertProductRatingSuccessSaveMessage
+ */
+class AssertProductRatingSuccessSaveMessage extends AbstractConstraint
+{
+    const SUCCESS_MESSAGE = 'You saved the rating.';
+
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'high';
+
+    /**
+     * Assert that success message is displayed after rating save
+     *
+     * @param RatingIndex $ratingIndex
+     * @return void
+     */
+    public function processAssert(RatingIndex $ratingIndex)
+    {
+        $actualMessage = $ratingIndex->getMessagesBlock()->getSuccessMessages();
+        \PHPUnit_Framework_Assert::assertEquals(
+            self::SUCCESS_MESSAGE,
+            $actualMessage,
+            'Wrong success message is displayed.'
+            . "\nExpected: " . self::SUCCESS_MESSAGE
+            . "\nActual: " . $actualMessage
+        );
+    }
+
+    /**
+     * Text success save message is displayed
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Rating success save message is present.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Fixture/Rating.php b/dev/tests/functional/tests/app/Magento/Review/Test/Fixture/Rating.php
new file mode 100644
index 00000000000..517aa62be43
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Fixture/Rating.php
@@ -0,0 +1,128 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\Fixture;
+
+use Mtf\Fixture\InjectableFixture;
+
+/**
+ * Class Rating
+ */
+class Rating extends InjectableFixture
+{
+    /**
+     * @var string
+     */
+    protected $repositoryClass = 'Magento\Rating\Test\Repository\Rating';
+
+    /**
+     * @var string
+     */
+    protected $handlerInterface = 'Magento\Rating\Test\Handler\Rating\RatingInterface';
+
+    protected $defaultDataSet = [
+        'rating_code' => 'Rating %isolation%',
+        'stores' => 'Main Website/Main Website Store/Default Store View',
+        'is_active' => 'Yes',
+    ];
+
+    protected $rating_id = [
+        'attribute_code' => 'rating_id',
+        'backend_type' => 'smallint',
+        'is_required' => '1',
+        'default_value' => '',
+        'input' => '',
+    ];
+
+    protected $entity_id = [
+        'attribute_code' => 'entity_id',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+    ];
+
+    protected $rating_code = [
+        'attribute_code' => 'rating_code',
+        'backend_type' => 'varchar',
+        'is_required' => '',
+        'default_value' => '',
+        'input' => '',
+        'group' => 'rating_information',
+    ];
+
+    protected $position = [
+        'attribute_code' => 'position',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '0',
+        'input' => '',
+        'group' => 'rating_information',
+    ];
+
+    protected $is_active = [
+        'attribute_code' => 'is_active',
+        'backend_type' => 'smallint',
+        'is_required' => '',
+        'default_value' => '1',
+        'input' => '',
+        'group' => 'rating_information',
+    ];
+
+    protected $stores = [
+        'attribute_code' => 'stores',
+        'backend_type' => 'virtual',
+        'group' => 'rating_information',
+    ];
+
+    public function getRatingId()
+    {
+        return $this->getData('rating_id');
+    }
+
+    public function getEntityId()
+    {
+        return $this->getData('entity_id');
+    }
+
+    public function getRatingCode()
+    {
+        return $this->getData('rating_code');
+    }
+
+    public function getPosition()
+    {
+        return $this->getData('position');
+    }
+
+    public function getIsActive()
+    {
+        return $this->getData('is_active');
+    }
+
+    public function getStores()
+    {
+        return $this->getData('stores');
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Fixture/Rating.xml b/dev/tests/functional/tests/app/Magento/Review/Test/Fixture/Rating.xml
new file mode 100644
index 00000000000..66e261cf218
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Fixture/Rating.xml
@@ -0,0 +1,79 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<fixture class="Magento\Review\Test\Fixture\Rating">
+    <module>Magento_Review</module>
+    <type>flat</type>
+    <entity_type>rating</entity_type>
+    <collection>Magento\Review\Model\Resource\Rating\Collection</collection>
+    <identifier>rating_code</identifier>
+    <fields>
+        <rating_id>
+            <attribute_code>rating_id</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required>1</is_required>
+            <default_value></default_value>
+            <input></input>
+        </rating_id>
+        <entity_id>
+            <attribute_code>entity_id</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+        </entity_id>
+        <rating_code>
+            <attribute_code>rating_code</attribute_code>
+            <backend_type>varchar</backend_type>
+            <is_required></is_required>
+            <default_value></default_value>
+            <input></input>
+            <group>rating_information</group>
+        </rating_code>
+        <position>
+            <attribute_code>position</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>0</default_value>
+            <input></input>
+            <group>rating_information</group>
+        </position>
+        <is_active>
+            <attribute_code>is_active</attribute_code>
+            <backend_type>smallint</backend_type>
+            <is_required></is_required>
+            <default_value>1</default_value>
+            <input></input>
+            <group>rating_information</group>
+        </is_active>
+        <stores>
+            <attribute_code>stores</attribute_code>
+            <backend_type>virtual</backend_type>
+            <group>rating_information</group>
+        </stores>
+    </fields>
+    <repository_class>Magento\Review\Test\Repository\Rating</repository_class>
+    <handler_interface>Magento\Review\Test\Handler\Rating\RatingInterface</handler_interface>
+</fixture>
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingEdit.php b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingEdit.php
new file mode 100644
index 00000000000..1addcbe56e0
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingEdit.php
@@ -0,0 +1,68 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\Page\Adminhtml;
+
+use Mtf\Page\BackendPage;
+
+/**
+ * Class RatingEdit
+ *
+ * @package Magento\Review\Test\Page\Adminhtml
+ */
+class RatingEdit extends BackendPage
+{
+    const MCA = 'review/rating/edit';
+
+    protected $_blocks = [
+        'pageActions' => [
+            'name' => 'pageActions',
+            'class' => 'Magento\Backend\Test\Block\FormPageActions',
+            'locator' => '.page-main-actions',
+            'strategy' => 'css selector',
+        ],
+        'ratingForm' => [
+            'name' => 'ratingForm',
+            'class' => 'Magento\Review\Test\Block\Adminhtml\Rating\Edit\RatingForm',
+            'locator' => '[id="page:main-container"]',
+            'strategy' => 'css selector',
+        ],
+    ];
+
+    /**
+     * @return \Magento\Backend\Test\Block\FormPageActions
+     */
+    public function getPageActions()
+    {
+        return $this->getBlockInstance('pageActions');
+    }
+
+    /**
+     * @return \Magento\Review\Test\Block\Adminhtml\Rating\Edit\RatingForm
+     */
+    public function getRatingForm()
+    {
+        return $this->getBlockInstance('ratingForm');
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingEdit.xml b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingEdit.xml
new file mode 100644
index 00000000000..5ef1dbc6ffb
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingEdit.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="review/rating/edit" >
+    <block>
+        <name>pageActions</name>
+        <class>Magento\Backend\Test\Block\FormPageActions</class>
+        <locator>.page-main-actions</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>ratingForm</name>
+        <class>Magento\Review\Test\Block\Adminhtml\Rating\Edit\RatingForm</class>
+        <locator>[id="page:main-container"]</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingIndex.php b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingIndex.php
new file mode 100644
index 00000000000..0ce1c13ebfb
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingIndex.php
@@ -0,0 +1,80 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\Page\Adminhtml;
+
+use Mtf\Page\BackendPage;
+
+/**
+ * Class RatingIndex
+ */
+class RatingIndex extends BackendPage
+{
+    const MCA = 'review/rating';
+
+    protected $_blocks = [
+        'messagesBlock' => [
+            'name' => 'messagesBlock',
+            'class' => 'Magento\Core\Test\Block\Messages',
+            'locator' => '#messages',
+            'strategy' => 'css selector',
+        ],
+        'gridPageActions' => [
+            'name' => 'gridPageActions',
+            'class' => 'Magento\Backend\Test\Block\GridPageActions',
+            'locator' => '.page-main-actions',
+            'strategy' => 'css selector',
+        ],
+        'ratingGrid' => [
+            'name' => 'ratingGrid',
+            'class' => 'Magento\Review\Test\Block\Adminhtml\Rating\Grid',
+            'locator' => '[id="page:main-container"]',
+            'strategy' => 'css selector',
+        ],
+    ];
+
+    /**
+     * @return \Magento\Core\Test\Block\Messages
+     */
+    public function getMessagesBlock()
+    {
+        return $this->getBlockInstance('messagesBlock');
+    }
+
+    /**
+     * @return \Magento\Backend\Test\Block\GridPageActions
+     */
+    public function getGridPageActions()
+    {
+        return $this->getBlockInstance('gridPageActions');
+    }
+
+    /**
+     * @return \Magento\Review\Test\Block\Adminhtml\Rating\Grid
+     */
+    public function getRatingGrid()
+    {
+        return $this->getBlockInstance('ratingGrid');
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingIndex.xml b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingIndex.xml
new file mode 100644
index 00000000000..4e766cebce6
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingIndex.xml
@@ -0,0 +1,45 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="review/rating" >
+    <block>
+        <name>messagesBlock</name>
+        <class>Magento\Core\Test\Block\Messages</class>
+        <locator>#messages</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>gridPageActions</name>
+        <class>Magento\Backend\Test\Block\GridPageActions</class>
+        <locator>.page-main-actions</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>ratingGrid</name>
+        <class>Magento\Review\Test\Block\Adminhtml\Rating\Grid</class>
+        <locator>[id="page:main-container"]</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingNew.php b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingNew.php
new file mode 100644
index 00000000000..63bc5b2c94c
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingNew.php
@@ -0,0 +1,66 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\Page\Adminhtml;
+
+use Mtf\Page\BackendPage;
+
+/**
+ * Class RatingNew
+ */
+class RatingNew extends BackendPage
+{
+    const MCA = 'review/rating/new';
+
+    protected $_blocks = [
+        'pageActions' => [
+            'name' => 'pageActions',
+            'class' => 'Magento\Backend\Test\Block\FormPageActions',
+            'locator' => '.page-main-actions',
+            'strategy' => 'css selector',
+        ],
+        'ratingForm' => [
+            'name' => 'ratingForm',
+            'class' => 'Magento\Review\Test\Block\Adminhtml\Rating\Edit\RatingForm',
+            'locator' => '[id="page:main-container"]',
+            'strategy' => 'css selector',
+        ],
+    ];
+
+    /**
+     * @return \Magento\Backend\Test\Block\FormPageActions
+     */
+    public function getPageActions()
+    {
+        return $this->getBlockInstance('pageActions');
+    }
+
+    /**
+     * @return \Magento\Review\Test\Block\Adminhtml\Rating\Edit\RatingForm
+     */
+    public function getRatingForm()
+    {
+        return $this->getBlockInstance('ratingForm');
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingNew.xml b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingNew.xml
new file mode 100644
index 00000000000..3a31c8fa841
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/Page/Adminhtml/RatingNew.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page mca="review/rating/new" >
+    <block>
+        <name>pageActions</name>
+        <class>Magento\Backend\Test\Block\FormPageActions</class>
+        <locator>.page-main-actions</locator>
+        <strategy>css selector</strategy>
+    </block>
+    <block>
+        <name>ratingForm</name>
+        <class>Magento\Review\Test\Block\Adminhtml\Rating\Edit\RatingForm</class>
+        <locator>[id="page:main-container"]</locator>
+        <strategy>css selector</strategy>
+    </block>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/TestCase/CreateBackendProductRatingTest.php b/dev/tests/functional/tests/app/Magento/Review/Test/TestCase/CreateBackendProductRatingTest.php
new file mode 100644
index 00000000000..e940b149769
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/TestCase/CreateBackendProductRatingTest.php
@@ -0,0 +1,129 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Review\Test\TestCase;
+
+use Magento\Review\Test\Page\Adminhtml\RatingIndex;
+use Magento\Review\Test\Page\Adminhtml\RatingNew;
+use Magento\Review\Test\Page\Adminhtml\RatingEdit;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Review\Test\Fixture\Rating;
+use Mtf\TestCase\Injectable;
+
+/**
+ * Test Creation for Create Backend Product Rating
+ *
+ * Test Flow:
+ *
+ * Preconditions:
+ * 1. Create simple product
+ *
+ * Steps:
+ * 1. Login to backend
+ * 2. Navigate Stores->Attributes->Rating
+ * 3. Add New Rating
+ * 4. Fill data according to dataset
+ * 5. Save Rating
+ * 6. Perform asserts
+ *
+ * @group Reviews_and_Ratings_(MX)
+ * @ZephyrId MAGETWO-23331
+ */
+class CreateBackendProductRatingTest extends Injectable
+{
+    /**
+     * @var Rating
+     */
+    protected $productRating;
+
+    /**
+     * @var RatingIndex
+     */
+    protected $ratingIndex;
+
+    /**
+     * @var RatingNew
+     */
+    protected $ratingNew;
+
+    /**
+     * @var RatingEdit
+     */
+    protected $ratingEdit;
+
+    /**
+     * Injection data
+     *
+     * @param RatingIndex $ratingIndex
+     * @param RatingNew $ratingNew
+     * @param RatingEdit $ratingEdit
+     * @return void
+     */
+    public function __inject(
+        RatingIndex $ratingIndex,
+        RatingNew $ratingNew,
+        RatingEdit $ratingEdit
+    ) {
+        $this->ratingIndex = $ratingIndex;
+        $this->ratingNew = $ratingNew;
+        $this->ratingEdit = $ratingEdit;
+    }
+
+    /**
+     * Run create backend Product Rating test
+     *
+     * @param CatalogProductSimple $product
+     * @param Rating $productRating
+     * @return void
+     */
+    public function testCreateBackendProductRating(
+        CatalogProductSimple $product,
+        Rating $productRating
+    ) {
+        // Preconditions
+        $product->persist();
+
+        // Steps
+        $this->ratingIndex->open();
+        $this->ratingIndex->getGridPageActions()->addNew();
+        $this->ratingNew->getRatingForm()->fill($productRating);
+        $this->ratingNew->getPageActions()->save();
+
+        // Prepare data for tear down
+        $this->productRating = $productRating;
+    }
+
+    /**
+     * Clear data after test
+     *
+     * @return void
+     */
+    public function tearDown()
+    {
+        $filter = ['rating_code' => $this->productRating->getRatingCode()];
+        $this->ratingIndex->open();
+        $this->ratingIndex->getRatingGrid()->searchAndOpen($filter);
+        $this->ratingEdit->getPageActions()->delete();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/TestCase/CreateBackendProductRatingTest/testCreateBackendProductRating.csv b/dev/tests/functional/tests/app/Magento/Review/Test/TestCase/CreateBackendProductRatingTest/testCreateBackendProductRating.csv
new file mode 100644
index 00000000000..e0465ef49d6
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/TestCase/CreateBackendProductRatingTest/testCreateBackendProductRating.csv
@@ -0,0 +1,3 @@
+"productRating/data/rating_code";"productRating/data/stores";"productRating/data/is_active";"constraint"
+"productRating_%isolation%";"Main Website/Main Website Store/Default Store View";"Yes";"assertProductRatingSuccessSaveMessage, assertProductRatingInGrid, assertProductRatingInProductPage"
+"productRating_%isolation%";"Main Website/Main Website Store/Default Store View";"No";"assertProductRatingSuccessSaveMessage, assertProductRatingInGrid, assertProductRatingNotInProductPage"
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/etc/global/constraint.xml b/dev/tests/functional/tests/app/Magento/Review/Test/etc/global/constraint.xml
new file mode 100644
index 00000000000..d69c444ee7c
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/etc/global/constraint.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" ?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<constraint>
+    <assertProductRatingSuccessSaveMessage module="Magento_Review">
+        <severeness>high</severeness>
+    </assertProductRatingSuccessSaveMessage>
+    <assertProductRatingInGrid module="Magento_Review">
+        <severeness>middle</severeness>
+    </assertProductRatingInGrid>
+    <assertProductRatingInProductPage module="Magento_Review">
+        <severeness>middle</severeness>
+    </assertProductRatingInProductPage>
+    <assertProductRatingNotInProductPage module="Magento_Review">
+        <severeness>middle</severeness>
+    </assertProductRatingNotInProductPage>
+</constraint>
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/etc/global/fixture.xml b/dev/tests/functional/tests/app/Magento/Review/Test/etc/global/fixture.xml
index 8795c998db9..0166d4b58be 100644
--- a/dev/tests/functional/tests/app/Magento/Review/Test/etc/global/fixture.xml
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/etc/global/fixture.xml
@@ -38,4 +38,12 @@
         <data_set />
         <data_config />
     </review>
+    <rating module="Magento_Review">
+        <type>flat</type>
+        <entity_type>rating</entity_type>
+        <collection>Magento\Review\Model\Resource\Rating\Collection</collection>
+        <identifier>rating_code</identifier>
+        <fields>
+        </fields>
+    </rating>
 </fixture>
diff --git a/dev/tests/functional/tests/app/Magento/Review/Test/etc/global/page.xml b/dev/tests/functional/tests/app/Magento/Review/Test/etc/global/page.xml
new file mode 100644
index 00000000000..073472b1b1e
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Review/Test/etc/global/page.xml
@@ -0,0 +1,42 @@
+<?xml version="1.0"?>
+<!--
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Academic Free License (AFL 3.0)
+ * that is bundled with this package in the file LICENSE_AFL.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/afl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
+ */
+-->
+<page>
+    <ratingIndex>
+        <mca>review/rating</mca>
+        <area>adminhtml</area>
+        <class>Magento\Review\Test\Page\Adminhtml\RatingIndex</class>
+    </ratingIndex>
+    <ratingNew>
+        <mca>review/rating/new</mca>
+        <area>adminhtml</area>
+        <class>Magento\Review\Test\Page\Adminhtml\RatingNew</class>
+    </ratingNew>
+    <ratingEdit>
+        <mca>review/rating/edit</mca>
+        <area>adminhtml</area>
+        <class>Magento\Review\Test\Page\Adminhtml\RatingEdit</class>
+    </ratingEdit>
+</page>
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/Edit/Form.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/Edit/Form.php
index 531eccf27ba..50530727ea8 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/Edit/Form.php
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/Edit/Form.php
@@ -24,13 +24,13 @@
 
 namespace Magento\Tax\Test\Block\Adminhtml\Rate\Edit;
 
-use Mtf\Block\Form as FormInterface;
+use Mtf\Block\Form as ParentForm;
 
 /**
  * Class Form
  * Form for tax rate creation
  */
-class Form extends FormInterface
+class Form extends ParentForm
 {
     //
 }
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/Edit/FormPageActions.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/Edit/FormPageActions.php
index 01f0c1fc60f..659a93a506a 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/Edit/FormPageActions.php
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/Edit/FormPageActions.php
@@ -24,13 +24,13 @@
 
 namespace Magento\Tax\Test\Block\Adminhtml\Rate\Edit;
 
-use Magento\Backend\Test\Block\FormPageActions as FormPageActionsInterface;
+use Magento\Backend\Test\Block\FormPageActions as ParentFormPageActions;
 
 /**
  * Class FormPageActions
  * Form page actions block in Tax Rate new/edit page
  */
-class FormPageActions extends FormPageActionsInterface
+class FormPageActions extends ParentFormPageActions
 {
     /**
      * "Save Rate" button
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/GridPageActions.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/GridPageActions.php
new file mode 100644
index 00000000000..63979f40233
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rate/GridPageActions.php
@@ -0,0 +1,41 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Tax\Test\Block\Adminhtml\Rate;
+
+use \Magento\Backend\Test\Block\GridPageActions as ParentGridPageActions;
+
+/**
+ * Class GridPageActions
+ * Grid page actions block in Tax Rate grid page
+ */
+class GridPageActions extends ParentGridPageActions
+{
+    /**
+     * "Add New Tax Rate" button
+     *
+     * @var string
+     */
+    protected $addNewButton = '.add-tax-rate';
+}
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rule/Grid.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rule/Grid.php
index 75f800359e2..97833ff1097 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rule/Grid.php
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Block/Adminhtml/Rule/Grid.php
@@ -67,9 +67,10 @@ class Grid extends GridInterface
      *
      * @param array $filter
      * @param bool $isSearchable
+     * @param bool $isStrict
      * @return bool
      */
-    public function isRowVisible(array $filter, $isSearchable = false)
+    public function isRowVisible(array $filter, $isSearchable = false, $isStrict = true)
     {
         $this->search(array('code' => $filter['code']));
         return parent::isRowVisible($filter, $isSearchable);
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRateForm.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRateForm.php
index 0e7fa32068b..6dddfefda14 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRateForm.php
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRateForm.php
@@ -18,8 +18,8 @@
  * versions in the future. If you wish to customize Magento for your
  * needs please refer to http://www.magentocommerce.com for more information.
  *
- * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
- * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ * @copyright Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
 namespace Magento\Tax\Test\Constraint;
@@ -103,13 +103,16 @@ class AssertTaxRateForm extends AbstractConstraint
     protected function verifyForm(array $formData, array $fixtureData)
     {
         $errorMessages = [];
+        $skippedFields = [
+            'id',
+        ];
 
         foreach ($fixtureData as $key => $value) {
-            if ($key === 'id') {
+            if (in_array($key, $skippedFields)) {
                 continue;
             }
             if ($value !== $formData[$key]) {
-                $errorMessages[] = "Data in " . $key . " field not equal."
+                $errorMessages[] = "Data in " . $key . " field is not equal."
                     . "\nExpected: " . $value
                     . "\nActual: " . $formData[$key];
             }
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRateInTaxRule.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRateInTaxRule.php
new file mode 100644
index 00000000000..9fea52aa720
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRateInTaxRule.php
@@ -0,0 +1,56 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Tax\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+
+/**
+ * Class AssertTaxRateInTaxRule
+ */
+class AssertTaxRateInTaxRule extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * @return void
+     */
+    public function processAssert()
+    {
+        //
+    }
+
+    /**
+     * @return string
+     */
+    public function toString()
+    {
+        //
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleApplying.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleApplying.php
new file mode 100644
index 00000000000..e6871d46fe9
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleApplying.php
@@ -0,0 +1,165 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Tax\Test\Constraint;
+
+use Magento\Catalog\Test\Page\Product\CatalogProductView;
+use Magento\Checkout\Test\Page\CheckoutCart;
+use Magento\Customer\Test\Fixture\AddressInjectable;
+use Magento\Customer\Test\Fixture\CustomerInjectable;
+use Magento\Customer\Test\Page\CustomerAccountLogin;
+use Magento\Customer\Test\Page\CustomerAccountLogout;
+use Magento\Catalog\Test\Fixture\CatalogProductSimple;
+use Magento\Tax\Test\Fixture\TaxRule;
+use Mtf\Constraint\AbstractConstraint;
+use Mtf\Fixture\FixtureFactory;
+
+/**
+ * Class AssertTaxRuleApplying
+ * Abstract class for implementing assert applying
+ */
+abstract class AssertTaxRuleApplying extends AbstractConstraint
+{
+    /**
+     * Initial tax rule
+     *
+     * @var TaxRule
+     */
+    protected $initialTaxRule;
+
+    /**
+     * Tax rule
+     *
+     * @var TaxRule
+     */
+    protected $taxRule;
+
+    /**
+     * Product simple
+     *
+     * @var CatalogProductSimple
+     */
+    protected $productSimple;
+
+    /**
+     * Checkout cart page
+     *
+     * @var CheckoutCart
+     */
+    protected $checkoutCart;
+
+    /**
+     * Shipping carrier and method
+     *
+     * @var array
+     */
+    protected $shipping;
+
+    /**
+     * Tax Rule name
+     *
+     * @var string
+     */
+    protected $taxRuleCode;
+
+    /**
+     * Implementation assert
+     *
+     * @return void
+     */
+    abstract protected function assert();
+
+    /**
+     * 1. Creating product simple with custom tax product class
+     * 2. Log In as customer
+     * 3. Add product to shopping cart
+     * 4. Estimate Shipping and Tax
+     * 5. Implementation assert
+     *
+     * @param FixtureFactory $fixtureFactory
+     * @param TaxRule $taxRule
+     * @param CustomerAccountLogin $customerAccountLogin
+     * @param CustomerAccountLogout $customerAccountLogout
+     * @param CustomerInjectable $customer
+     * @param CatalogProductView $catalogProductView
+     * @param CheckoutCart $checkoutCart
+     * @param AddressInjectable $address
+     * @param array $shipping
+     * @param TaxRule $initialTaxRule
+     * @return void
+     */
+    public function processAssert(
+        FixtureFactory $fixtureFactory,
+        TaxRule $taxRule,
+        CustomerAccountLogin $customerAccountLogin,
+        CustomerAccountLogout $customerAccountLogout,
+        CustomerInjectable $customer,
+        CatalogProductView $catalogProductView,
+        CheckoutCart $checkoutCart,
+        AddressInjectable $address,
+        array $shipping,
+        TaxRule $initialTaxRule = null
+    ) {
+        $this->initialTaxRule = $initialTaxRule;
+        $this->taxRule = $taxRule;
+        $this->checkoutCart = $checkoutCart;
+        $this->shipping = $shipping;
+
+        if ($this->initialTaxRule !== null) {
+            $this->taxRuleCode = ($this->taxRule->hasData('code'))
+                ? $this->taxRule->getCode()
+                : $this->initialTaxRule->getCode();
+        } else {
+            $this->taxRuleCode = $this->taxRule->getCode();
+        }
+        // Creating simple product with custom tax class
+        /** @var \Magento\Tax\Test\Fixture\TaxClass $taxProductClass */
+        $taxProductClass = $taxRule->getDataFieldConfig('tax_product_class')['source']->getFixture()[0];
+        $this->productSimple = $fixtureFactory->createByCode(
+            'catalogProductSimple',
+            [
+                'dataSet' => '100_dollar_product_for_tax_rule',
+                'data' => [
+                    'tax_class_id' => ['tax_product_class' => $taxProductClass],
+                ]
+            ]
+        );
+        $this->productSimple->persist();
+        // Customer login
+        $customerAccountLogout->open();
+        $customerAccountLogin->open();
+        $customerAccountLogin->getLoginBlock()->login($customer);
+        // Clearing shopping cart and adding product to shopping cart
+        $checkoutCart->open()->getCartBlock()->clearShoppingCart();
+        $catalogProductView->init($this->productSimple);
+        $catalogProductView->open();
+        $catalogProductView->getViewBlock()->clickAddToCart();
+        // Estimate Shipping and Tax
+        $checkoutCart->getShippingBlock()->openEstimateShippingAndTax();
+        $checkoutCart->getShippingBlock()->fill($address);
+        $checkoutCart->getShippingBlock()->clickGetQuote();
+        $checkoutCart->getShippingBlock()->selectShippingMethod($shipping);
+        $this->assert();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleIsApplied.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleIsApplied.php
index 94f6c54145f..f319901e801 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleIsApplied.php
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleIsApplied.php
@@ -24,20 +24,10 @@
 
 namespace Magento\Tax\Test\Constraint;
 
-use Magento\Catalog\Test\Fixture\CatalogProductSimple;
-use Magento\Catalog\Test\Page\Product\CatalogProductView;
-use Magento\Checkout\Test\Page\CheckoutCart;
-use Magento\Customer\Test\Fixture\AddressInjectable;
-use Magento\Customer\Test\Fixture\CustomerInjectable;
-use Magento\Customer\Test\Page\CustomerAccountLogin;
-use Magento\Customer\Test\Page\CustomerAccountLogout;
-use Magento\Tax\Test\Fixture\TaxRule;
-use Mtf\Constraint\AbstractConstraint;
-
 /**
  * Class AssertTaxRuleIsApplied
  */
-class AssertTaxRuleIsApplied extends AbstractConstraint
+class AssertTaxRuleIsApplied extends AssertTaxRuleApplying
 {
     /**
      * Constraint severeness
@@ -49,54 +39,23 @@ class AssertTaxRuleIsApplied extends AbstractConstraint
     /**
      * Assert that tax rule is applied on product in shopping cart.
      *
-     * @param TaxRule $taxRule
-     * @param CustomerAccountLogin $customerAccountLogin
-     * @param CustomerAccountLogout $customerAccountLogout
-     * @param CustomerInjectable $customer
-     * @param CatalogProductView $catalogProductView
-     * @param CatalogProductSimple $productSimple
-     * @param CheckoutCart $checkoutCart
-     * @param AddressInjectable $address
-     * @param array $shipping
      * @return void
      */
-    public function processAssert(
-        TaxRule $taxRule,
-        CustomerAccountLogin $customerAccountLogin,
-        CustomerAccountLogout $customerAccountLogout,
-        CustomerInjectable $customer,
-        CatalogProductView $catalogProductView,
-        CatalogProductSimple $productSimple,
-        CheckoutCart $checkoutCart,
-        AddressInjectable $address,
-        array $shipping
-    ) {
+    protected function assert()
+    {
         $errorMessages = [];
-        // Customer login
-        $customerAccountLogout->open();
-        $customerAccountLogin->open();
-        $customerAccountLogin->getLoginBlock()->login($customer);
-        // Clearing shopping cart and adding product to shopping cart
-        $checkoutCart->open()->getCartBlock()->clearShoppingCart();
-        $catalogProductView->init($productSimple);
-        $catalogProductView->open();
-        $catalogProductView->getViewBlock()->clickAddToCart();
-        // Estimate Shipping and Tax
-        $checkoutCart->getShippingBlock()->openEstimateShippingAndTax();
-        $checkoutCart->getShippingBlock()->fill($address);
-        $checkoutCart->getShippingBlock()->clickGetQuote();
-        $checkoutCart->getShippingBlock()->selectShippingMethod($shipping);
+
         // Preparing data to compare
-        $taxRate = $taxRule->getDataFieldConfig('tax_rate')['source']->getFixture()[0]->getRate();
-        $expectedGrandTotal = $productSimple->getPrice() + $taxRate + $shipping['price'];
+        $taxRate = $this->taxRule->getDataFieldConfig('tax_rate')['source']->getFixture()[0]->getRate();
+        $expectedGrandTotal = $this->productSimple->getPrice() + $taxRate + $this->shipping['price'];
         $expectedGrandTotal = number_format($expectedGrandTotal, 2);
-        $actualGrandTotal = $checkoutCart->getTotalsBlock()->getGrandTotal();
+        $actualGrandTotal = $this->checkoutCart->getTotalsBlock()->getGrandTotal();
 
-        if ($checkoutCart->getTotalsBlock()->isTaxVisible()) {
+        if ($this->checkoutCart->getTotalsBlock()->isTaxVisible()) {
             $expectedTax = number_format($taxRate, 2);
-            $actualTax = $checkoutCart->getTotalsBlock()->getTax();
+            $actualTax = $this->checkoutCart->getTotalsBlock()->getTax();
             if ($expectedTax !== $actualTax) {
-                $errorMessages[] = 'Tax is not correct.'
+                $errorMessages[] = 'Tax Rule \'' . $this->taxRuleCode . '\' is applied wrong.'
                     . "\nExpected: " . $expectedTax
                     . "\nActual: " . $actualTax;
             }
@@ -107,10 +66,7 @@ class AssertTaxRuleIsApplied extends AbstractConstraint
                 . "\nActual: " . $actualGrandTotal;
         }
 
-        \PHPUnit_Framework_Assert::assertTrue(
-            empty($errorMessages),
-            implode(";\n", $errorMessages)
-        );
+        \PHPUnit_Framework_Assert::assertTrue(empty($errorMessages), implode(";\n", $errorMessages));
     }
 
     /**
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleIsNotApplied.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleIsNotApplied.php
index c80b20ad4fd..53179ad0ca5 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleIsNotApplied.php
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleIsNotApplied.php
@@ -24,20 +24,10 @@
 
 namespace Magento\Tax\Test\Constraint;
 
-use Magento\Catalog\Test\Fixture\CatalogProductSimple;
-use Magento\Catalog\Test\Page\Product\CatalogProductView;
-use Magento\Checkout\Test\Page\CheckoutCart;
-use Magento\Customer\Test\Fixture\AddressInjectable;
-use Magento\Customer\Test\Fixture\CustomerInjectable;
-use Magento\Customer\Test\Page\CustomerAccountLogin;
-use Magento\Customer\Test\Page\CustomerAccountLogout;
-use Magento\Tax\Test\Fixture\TaxRule;
-use Mtf\Constraint\AbstractConstraint;
-
 /**
  * Class AssertTaxRuleIsNotApplied
  */
-class AssertTaxRuleIsNotApplied extends AbstractConstraint
+class AssertTaxRuleIsNotApplied extends AssertTaxRuleApplying
 {
     /**
      * Constraint severeness
@@ -49,57 +39,19 @@ class AssertTaxRuleIsNotApplied extends AbstractConstraint
     /**
      * Assert that tax rule is not applied on product in shopping cart.
      *
-     * @param TaxRule $taxRule
-     * @param CustomerAccountLogin $customerAccountLogin
-     * @param CustomerAccountLogout $customerAccountLogout
-     * @param CustomerInjectable $customer
-     * @param CatalogProductView $catalogProductView
-     * @param CatalogProductSimple $productSimple
-     * @param CheckoutCart $checkoutCart
-     * @param AddressInjectable $address
-     * @param array $shipping
-     * @param TaxRule $initialTaxRule
      * @return void
      */
-    public function processAssert(
-        TaxRule $taxRule,
-        CustomerAccountLogin $customerAccountLogin,
-        CustomerAccountLogout $customerAccountLogout,
-        CustomerInjectable $customer,
-        CatalogProductView $catalogProductView,
-        CatalogProductSimple $productSimple,
-        CheckoutCart $checkoutCart,
-        AddressInjectable $address,
-        array $shipping,
-        TaxRule $initialTaxRule = null
-    ) {
+    protected function assert()
+    {
         $errorMessages = [];
-        if ($initialTaxRule !== null) {
-            $taxRuleCode = ($taxRule->hasData('code')) ? $taxRule->getCode() : $initialTaxRule->getCode();
-        } else {
-            $taxRuleCode = $taxRule->getCode();
-        }
-        // Customer login
-        $customerAccountLogout->open();
-        $customerAccountLogin->open();
-        $customerAccountLogin->getLoginBlock()->login($customer);
-        // Clearing shopping cart and adding product to shopping cart
-        $checkoutCart->open()->getCartBlock()->clearShoppingCart();
-        $catalogProductView->init($productSimple);
-        $catalogProductView->open();
-        $catalogProductView->getViewBlock()->clickAddToCart();
-        // Estimate Shipping and Tax
-        $checkoutCart->getShippingBlock()->openEstimateShippingAndTax();
-        $checkoutCart->getShippingBlock()->fill($address);
-        $checkoutCart->getShippingBlock()->clickGetQuote();
-        $checkoutCart->getShippingBlock()->selectShippingMethod($shipping);
+
         // Preparing data to compare
-        $expectedGrandTotal = $productSimple->getPrice() + $shipping['price'];
+        $expectedGrandTotal = $this->productSimple->getPrice() + $this->shipping['price'];
         $expectedGrandTotal = number_format($expectedGrandTotal, 2);
-        $actualGrandTotal = $checkoutCart->getTotalsBlock()->getGrandTotal();
+        $actualGrandTotal = $this->checkoutCart->getTotalsBlock()->getGrandTotal();
 
-        if ($checkoutCart->getTotalsBlock()->isTaxVisible()) {
-            $errorMessages[] = 'Tax Rule \'' . $taxRuleCode . '\' present in shopping cart.';
+        if ($this->checkoutCart->getTotalsBlock()->isTaxVisible()) {
+            $errorMessages[] = 'Tax Rule \'' . $this->taxRuleCode . '\' present in shopping cart.';
         }
         if ($expectedGrandTotal !== $actualGrandTotal) {
             $errorMessages[] = 'Grand Total is not correct.'
@@ -107,10 +59,7 @@ class AssertTaxRuleIsNotApplied extends AbstractConstraint
                 . "\nActual: " . $actualGrandTotal;
         }
 
-        \PHPUnit_Framework_Assert::assertTrue(
-            empty($errorMessages),
-            implode(";\n", $errorMessages)
-        );
+        \PHPUnit_Framework_Assert::assertTrue(empty($errorMessages), implode(";\n", $errorMessages));
     }
 
     /**
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleNotInGrid.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleNotInGrid.php
new file mode 100644
index 00000000000..84ef828239d
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleNotInGrid.php
@@ -0,0 +1,74 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Tax\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Tax\Test\Page\Adminhtml\TaxRuleIndex;
+use Magento\Tax\Test\Fixture\TaxRule;
+
+/**
+ * Class AssertTaxRuleNotInGrid
+ */
+class AssertTaxRuleNotInGrid extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'high';
+
+    /**
+     * Assert that tax rule not available in Tax Rule grid
+     *
+     * @param TaxRuleIndex $taxRuleIndex
+     * @param TaxRule $taxRule
+     * @return void
+     */
+    public function processAssert(
+        TaxRuleIndex $taxRuleIndex,
+        TaxRule $taxRule
+    ) {
+        $filter = [
+            'code' => $taxRule->getCode(),
+        ];
+
+        $taxRuleIndex->open();
+        \PHPUnit_Framework_Assert::assertFalse(
+            $taxRuleIndex->getTaxRuleGrid()->isRowVisible($filter),
+            'Tax Rule \'' . $filter['code'] . '\' is present in Tax Rule grid.'
+        );
+    }
+
+    /**
+     * Text of Tax Rule not in grid assert
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Tax rule is absent in grid.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleSuccessDeleteMessage.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleSuccessDeleteMessage.php
new file mode 100644
index 00000000000..7a7aa9158f7
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Constraint/AssertTaxRuleSuccessDeleteMessage.php
@@ -0,0 +1,71 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Tax\Test\Constraint;
+
+use Mtf\Constraint\AbstractConstraint;
+use Magento\Tax\Test\Page\Adminhtml\TaxRuleIndex;
+
+/**
+ * Class AssertTaxRuleSuccessDeleteMessage
+ */
+class AssertTaxRuleSuccessDeleteMessage extends AbstractConstraint
+{
+    const SUCCESS_DELETE_MESSAGE = 'The tax rule has been deleted.';
+
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'high';
+
+    /**
+     * Assert that success delete message is displayed after tax rule deleted
+     *
+     * @param TaxRuleIndex $taxRuleIndex
+     * @return void
+     */
+    public function processAssert(TaxRuleIndex $taxRuleIndex)
+    {
+        $actualMessage = $taxRuleIndex->getMessagesBlock()->getSuccessMessages();
+        \PHPUnit_Framework_Assert::assertEquals(
+            self::SUCCESS_DELETE_MESSAGE,
+            $actualMessage,
+            'Wrong success delete message is displayed.'
+            . "\nExpected: " . self::SUCCESS_DELETE_MESSAGE
+            . "\nActual: " . $actualMessage
+        );
+    }
+
+    /**
+     * Text of Deleted Tax Rule Success Message assert
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Tax rule success delete message is present.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Page/Adminhtml/TaxRateIndex.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Page/Adminhtml/TaxRateIndex.php
index 9d7384ad5fa..08331040ede 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/Page/Adminhtml/TaxRateIndex.php
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Page/Adminhtml/TaxRateIndex.php
@@ -36,7 +36,7 @@ class TaxRateIndex extends BackendPage
     protected $_blocks = [
         'gridPageActions' => [
             'name' => 'gridPageActions',
-            'class' => 'Magento\Backend\Test\Block\GridPageActions',
+            'class' => 'Magento\Tax\Test\Block\Adminhtml\Rate\GridPageActions',
             'locator' => '.page-main-actions',
             'strategy' => 'css selector',
         ],
@@ -55,7 +55,7 @@ class TaxRateIndex extends BackendPage
     ];
 
     /**
-     * @return \Magento\Backend\Test\Block\GridPageActions
+     * @return \Magento\Tax\Test\Block\Adminhtml\Rate\GridPageActions
      */
     public function getGridPageActions()
     {
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Page/Adminhtml/TaxRateIndex.xml b/dev/tests/functional/tests/app/Magento/Tax/Test/Page/Adminhtml/TaxRateIndex.xml
index 6de779d910f..f5a4adaef48 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/Page/Adminhtml/TaxRateIndex.xml
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Page/Adminhtml/TaxRateIndex.xml
@@ -26,7 +26,7 @@
 <page mca="tax/rate/index" >
     <block>
         <name>gridPageActions</name>
-        <class>Magento\Backend\Test\Block\GridPageActions</class>
+        <class>Magento\Tax\Test\Block\Adminhtml\Rate\GridPageActions</class>
         <locator>.page-main-actions</locator>
         <strategy>css selector</strategy>
     </block>
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Repository/TaxClass.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Repository/TaxClass.php
index bfbc4b50cb0..57bf7d25d79 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/Repository/TaxClass.php
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Repository/TaxClass.php
@@ -58,5 +58,15 @@ class TaxClass extends AbstractRepository
             'class_name' => 'Product Tax Class %isolation%',
             'class_type' => 'PRODUCT',
         ];
+
+        $this->_data['None'] = [
+            'class_name' => 'None',
+            'class_type' => 'PRODUCT',
+            'id' => '0',
+        ];
+
+        $this->_data['all'] = [
+            'class_name' => 'All',
+        ];
     }
 }
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/Repository/TaxRule.php b/dev/tests/functional/tests/app/Magento/Tax/Test/Repository/TaxRule.php
index 2b57af9581d..00ad6fa0e5f 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/Repository/TaxRule.php
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/Repository/TaxRule.php
@@ -113,8 +113,8 @@ class TaxRule extends AbstractRepository
             ],
             'tax_product_class' => [
                 'dataSet' => [
-                    0 => 'Taxable Goods',
-                    1 => 'product_tax_class',
+                    0 => 'product_tax_class',
+                    1 => 'Taxable Goods',
                 ],
             ],
             'priority' => '1',
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/CreateTaxRateEntityTest.php b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/CreateTaxRateEntityTest.php
new file mode 100644
index 00000000000..2c90126ea5d
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/CreateTaxRateEntityTest.php
@@ -0,0 +1,92 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Tax\Test\TestCase;
+
+use Magento\Tax\Test\Fixture\TaxRate;
+use Magento\Tax\Test\Page\Adminhtml\TaxRateIndex;
+use Magento\Tax\Test\Page\Adminhtml\TaxRateNew;
+use Mtf\TestCase\Injectable;
+
+/**
+ * Test Creation for CreateTaxRateEntity
+ *
+ * Test Flow:
+ * Steps:
+ * 1. Log in as default admin user.
+ * 2. Go to Stores > Taxes > Tax Zones and Rates.
+ * 3. Click 'Add New Tax Rate' button.
+ * 4. Fill in data according to dataSet
+ * 5. Save Tax Rate.
+ * 6. Perform all assertions.
+ *
+ * @group Tax_(CS)
+ * @ZephyrId MAGETWO-23286
+ */
+class CreateTaxRateEntityTest extends Injectable
+{
+    /**
+     * Tax Rate grid page
+     *
+     * @var TaxRateIndex
+     */
+    protected $taxRateIndexPage;
+
+    /**
+     * Tax Rate new/edit page
+     *
+     * @var TaxRateNew
+     */
+    protected $taxRateNewPage;
+
+    /**
+     * Injection data
+     *
+     * @param TaxRateIndex $taxRateIndexPage
+     * @param TaxRateNew $taxRateNewPage
+     * @return void
+     */
+    public function __inject(
+        TaxRateIndex $taxRateIndexPage,
+        TaxRateNew $taxRateNewPage
+    ) {
+        $this->taxRateIndexPage = $taxRateIndexPage;
+        $this->taxRateNewPage = $taxRateNewPage;
+    }
+
+    /**
+     * Create Tax Rate Entity test
+     *
+     * @param TaxRate $taxRate
+     * @return void
+     */
+    public function testCreateTaxRate(TaxRate $taxRate)
+    {
+        // Steps
+        $this->taxRateIndexPage->open();
+        $this->taxRateIndexPage->getGridPageActions()->addNew();
+        $this->taxRateNewPage->getTaxRateForm()->fill($taxRate);
+        $this->taxRateNewPage->getFormPageActions()->save();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/CreateTaxRateEntityTest/testCreateTaxRate.csv b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/CreateTaxRateEntityTest/testCreateTaxRate.csv
new file mode 100644
index 00000000000..7fe1d4458ff
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/CreateTaxRateEntityTest/testCreateTaxRate.csv
@@ -0,0 +1,6 @@
+"taxRate/data/code";"taxRate/data/zip_is_range";"taxRate/data/zip_from";"taxRate/data/zip_to";"taxRate/data/tax_postcode";"taxRate/data/tax_country_id";"taxRate/data/tax_region_id";"taxRate/data/rate";"constraint"
+"TaxIdentifier%isolation%";"No";"-";"-";"*";"Australia";"*";"20";"assertTaxRateSuccessSaveMessage, assertTaxRateInGrid, assertTaxRateForm, assertTaxRateInTaxRule"
+"TaxIdentifier%isolation%";"Yes";"90001";"96162";"-";"United States";"California";"15.5";"assertTaxRateSuccessSaveMessage, assertTaxRateInGrid, assertTaxRateForm, assertTaxRateInTaxRule"
+"TaxIdentifier%isolation%";"No";"-";"-";"180";"Canada";"*";"25";"assertTaxRateSuccessSaveMessage, assertTaxRateInGrid, assertTaxRateForm, assertTaxRateInTaxRule"
+"TaxIdentifier%isolation%";"Yes";"0";"7800935";"-";"United Kingdom";"*";"0";"assertTaxRateIsInCorrectRange"
+"TaxIdentifier%isolation%";"No";"-";"-";"*";"France";"Val-d'Oise";"999";"assertTaxRateIsInCorrectRange"
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/DeleteTaxRuleEntityTest.php b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/DeleteTaxRuleEntityTest.php
new file mode 100644
index 00000000000..46a92ba977d
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/DeleteTaxRuleEntityTest.php
@@ -0,0 +1,118 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Tax\Test\TestCase;
+
+use Magento\Customer\Test\Fixture\AddressInjectable;
+use Magento\Tax\Test\Fixture\TaxRule;
+use Magento\Tax\Test\Page\Adminhtml\TaxRuleIndex;
+use Magento\Tax\Test\Page\Adminhtml\TaxRuleNew;
+use Mtf\Fixture\FixtureFactory;
+use Mtf\TestCase\Injectable;
+
+/**
+ * Test Creation for Delete TaxRuleEntity
+ *
+ * Test Flow:
+ * Preconditions:
+ * 1. Tax Rule is created
+ *
+ * Steps:
+ * 1. Log in as default admin user.
+ * 2. Go to Sales > Tax Rules
+ * 3. Select required tax rule from preconditions
+ * 4. Click on the "Delete Rule" button
+ * 5. Perform all assertions
+ *
+ * @group Tax_(CS)
+ * @ZephyrId MAGETWO-20924
+ */
+class DeleteTaxRuleEntityTest extends Injectable
+{
+    /**
+     * Tax Rule grid page
+     *
+     * @var TaxRuleIndex
+     */
+    protected $taxRuleIndexPage;
+
+    /**
+     * Tax Rule new and edit page
+     *
+     * @var TaxRuleNew
+     */
+    protected $taxRuleNewPage;
+
+    /**
+     * Preparing data
+     *
+     * @param FixtureFactory $fixtureFactory
+     * @return array
+     */
+    public function __prepare(FixtureFactory $fixtureFactory)
+    {
+        $customer = $fixtureFactory->createByCode('customerInjectable', ['dataSet' => 'default']);
+        $customer->persist();
+
+        return ['customer' => $customer];
+    }
+
+    /**
+     * Injection data
+     *
+     * @param TaxRuleIndex $taxRuleIndexPage
+     * @param TaxRuleNew $taxRuleNewPage
+     */
+    public function __inject(
+        TaxRuleIndex $taxRuleIndexPage,
+        TaxRuleNew $taxRuleNewPage
+    ) {
+        $this->taxRuleIndexPage = $taxRuleIndexPage;
+        $this->taxRuleNewPage = $taxRuleNewPage;
+    }
+
+    /**
+     * Delete Tax Rule Entity test
+     *
+     * @param TaxRule $taxRule
+     * @param AddressInjectable $address
+     * @param array $shipping
+     */
+    public function testDeleteTaxRule(
+        TaxRule $taxRule,
+        AddressInjectable $address,
+        array $shipping
+    ) {
+        // Precondition
+        $taxRule->persist();
+
+        // Steps
+        $filters = [
+            'code' => $taxRule->getCode(),
+        ];
+        $this->taxRuleIndexPage->open();
+        $this->taxRuleIndexPage->getTaxRuleGrid()->searchAndOpen($filters);
+        $this->taxRuleNewPage->getFormPageActions()->delete();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/DeleteTaxRuleEntityTest/testDeleteTaxRule.csv b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/DeleteTaxRuleEntityTest/testDeleteTaxRule.csv
new file mode 100644
index 00000000000..a176ebbffba
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/DeleteTaxRuleEntityTest/testDeleteTaxRule.csv
@@ -0,0 +1,2 @@
+"taxRule/dataSet";"address/data/country_id";"address/data/region_id";"address/data/postcode";"shipping/carrier";"shipping/method";"shipping/price";"constraint"
+"tax_rule_with_custom_tax_classes";"United States";"California";90001;"Flat Rate";"Fixed";5;"assertTaxRuleSuccessDeleteMessage, assertTaxRuleNotInGrid, assertTaxRuleIsNotApplied"
\ No newline at end of file
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/UpdateTaxRuleEntityTest.php b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/UpdateTaxRuleEntityTest.php
index 0f8e0b7b9bb..41008abe979 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/UpdateTaxRuleEntityTest.php
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/UpdateTaxRuleEntityTest.php
@@ -74,15 +74,10 @@ class UpdateTaxRuleEntityTest extends Injectable
      */
     public function __prepare(FixtureFactory $fixtureFactory)
     {
-        $productSimple = $fixtureFactory->createByCode('catalogProductSimple', ['dataSet' => '100_dollar_product']);
-        $productSimple->persist();
         $customer = $fixtureFactory->createByCode('customerInjectable', ['dataSet' => 'default']);
         $customer->persist();
 
-        return [
-            'productSimple' => $productSimple,
-            'customer' => $customer,
-        ];
+        return ['customer' => $customer];
     }
 
     /**
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/UpdateTaxRuleEntityTest/testUpdateTaxRule.csv b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/UpdateTaxRuleEntityTest/testUpdateTaxRule.csv
index b87c02bedf6..a2cf2048159 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/UpdateTaxRuleEntityTest/testUpdateTaxRule.csv
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/TestCase/UpdateTaxRuleEntityTest/testUpdateTaxRule.csv
@@ -1,5 +1,5 @@
-"initialTaxRule/dataSet";"address/data/country_id";"address/data/region_id";"address/data/postcode";"shipping/carrier";"shipping/method";"shipping/price";"taxRule/data/code";"taxRule/data/tax_rate/dataSet/rate_0";"taxRule/data/tax_customer_class/dataSet/class_0";"taxRule/data/tax_product_class/dataSet/class_0";"taxRule/data/priority";"taxRule/data/position";"constraint"
-"tax_rule_default";"-";"-";"-";"-";"-";"-";"New Tax Rule name%isolation%";"default";"customer_tax_class";"product_tax_class";"2";"2";"assertTaxRuleSuccessSaveMessage, assertTaxRuleInGrid, assertTaxRuleForm"
-"tax_rule_with_custom_tax_classes";"-";"-";"-";"-";"-";"-";"-";"withZipRange";"Retail Customer";"Taxable Goods";"-";"-";"assertTaxRuleSuccessSaveMessage, assertTaxRuleInGrid, assertTaxRuleForm"
-"tax_rule_with_custom_tax_classes";"United States";"Utah";84001;"Flat Rate";"Fixed";5;"-";"us_ut_fixed_zip_rate_20";"-";"-";"-";"-";"assertTaxRuleSuccessSaveMessage, assertTaxRuleInGrid, assertTaxRuleForm, assertTaxRuleIsApplied"
-"tax_rule_with_custom_tax_classes";"United States";"Idaho";83201;"Flat Rate";"Fixed";5;"-";"withFixedZip";"-";"-";"-";"-";"assertTaxRuleSuccessSaveMessage, assertTaxRuleInGrid, assertTaxRuleForm, assertTaxRuleIsNotApplied"
\ No newline at end of file
+"initialTaxRule/dataSet";"address/data/country_id";"address/data/region_id";"address/data/postcode";"shipping/carrier";"shipping/method";"shipping/price";"taxRule/data/code";"taxRule/data/tax_rate/dataSet/rate_0";"taxRule/data/tax_customer_class/dataSet/class_0";"taxRule/data/tax_product_class/dataSet/class_0";"taxRule/data/tax_product_class/dataSet/class_1";"taxRule/data/priority";"taxRule/data/position";"constraint"
+"tax_rule_default";"-";"-";"-";"-";"-";"-";"New Tax Rule name%isolation%";"default";"customer_tax_class";"product_tax_class";"product_tax_class";"2";"2";"assertTaxRuleSuccessSaveMessage, assertTaxRuleInGrid, assertTaxRuleForm"
+"tax_rule_with_custom_tax_classes";"-";"-";"-";"-";"-";"-";"-";"withZipRange";"Retail Customer";"product_tax_class";"Taxable Goods";"-";"-";"assertTaxRuleSuccessSaveMessage, assertTaxRuleInGrid, assertTaxRuleForm"
+"tax_rule_with_custom_tax_classes";"United States";"Utah";84001;"Flat Rate";"Fixed";5;"-";"us_ut_fixed_zip_rate_20";"-";"product_tax_class";"-";"-";"-";"assertTaxRuleSuccessSaveMessage, assertTaxRuleInGrid, assertTaxRuleForm, assertTaxRuleIsApplied"
+"tax_rule_with_custom_tax_classes";"United States";"Idaho";83201;"Flat Rate";"Fixed";5;"-";"withFixedZip";"-";"product_tax_class";"-";"-";"-";"assertTaxRuleSuccessSaveMessage, assertTaxRuleInGrid, assertTaxRuleForm, assertTaxRuleIsNotApplied"
\ No newline at end of file
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/etc/curl/di.xml b/dev/tests/functional/tests/app/Magento/Tax/Test/etc/curl/di.xml
index a27f5a1e18d..d3f761e53f7 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/etc/curl/di.xml
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/etc/curl/di.xml
@@ -23,7 +23,7 @@
  * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
  */
 -->
-<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../../../../lib/Magento/Framework/ObjectManager/etc/config.xsd">
+<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../../../../lib/internal/Magento/Framework/ObjectManager/etc/config.xsd">
     <preference for="\Magento\Tax\Test\Handler\TaxRule\TaxRuleInterface" type="\Magento\Tax\Test\Handler\TaxRule\Curl" />
     <preference for="\Magento\Tax\Test\Handler\TaxRate\TaxRateInterface" type="\Magento\Tax\Test\Handler\TaxRate\Curl" />
     <preference for="\Magento\Tax\Test\Handler\TaxClass\TaxClassInterface" type="\Magento\Tax\Test\Handler\TaxClass\Curl" />
diff --git a/dev/tests/functional/tests/app/Magento/Tax/Test/etc/global/constraint.xml b/dev/tests/functional/tests/app/Magento/Tax/Test/etc/global/constraint.xml
index fa9046b598b..3e353cf8a61 100644
--- a/dev/tests/functional/tests/app/Magento/Tax/Test/etc/global/constraint.xml
+++ b/dev/tests/functional/tests/app/Magento/Tax/Test/etc/global/constraint.xml
@@ -70,6 +70,10 @@
         <severeness>low</severeness>
         <require/>
     </assertTaxRateIsInCorrectRange>
+    <assertTaxRateInTaxRule module="Magento_Tax">
+        <severeness>low</severeness>
+        <require/>
+    </assertTaxRateInTaxRule>
     <assertTaxRuleIsApplied module="Magento_Tax">
         <severeness>high</severeness>
         <require />
@@ -78,4 +82,17 @@
         <severeness>high</severeness>
         <require />
     </assertTaxRuleIsNotApplied>
+    <assertTaxRuleSuccessDeleteMessage module="Magento_Tax">
+        <severeness>high</severeness>
+        <require>
+            <taxRuleIndex class="Magento\Tax\Test\Page\Adminhtml\TaxRuleIndex" />
+        </require>
+    </assertTaxRuleSuccessDeleteMessage>
+    <assertTaxRuleNotInGrid module="Magento_Tax">
+        <severeness>high</severeness>
+        <require>
+            <taxRuleIndex class="Magento\Tax\Test\Page\Adminhtml\TaxRuleIndex" />
+            <taxRule class="Magento\Tax\Test\Fixture\TaxRule" />
+        </require>
+    </assertTaxRuleNotInGrid>
 </constraint>
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Constraint/AssertProductUrlAvailableOnTheFront.php b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Constraint/AssertProductUrlAvailableOnTheFront.php
new file mode 100644
index 00000000000..298b499c219
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Constraint/AssertProductUrlAvailableOnTheFront.php
@@ -0,0 +1,77 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\UrlRewrite\Test\Constraint;
+
+use Magento\Catalog\Test\Page\Product\CatalogProductView;
+use Mtf\Client\Browser;
+use Mtf\Constraint\AbstractConstraint;
+use Magento\UrlRewrite\Test\Fixture\UrlRewrite;
+
+/**
+ * Class AssertProductUrlAvailableOnTheFront
+ * Assert that product available by new URL on the front
+ */
+class AssertProductUrlAvailableOnTheFront extends AbstractConstraint
+{
+    /**
+     * Constraint severeness
+     *
+     * @var string
+     */
+    protected $severeness = 'low';
+
+    /**
+     * Check that product available by new URL on the front
+     *
+     * @param UrlRewrite $urlRewrite
+     * @param CatalogProductView $catalogProductView
+     * @param Browser $browser
+     * @return void
+     */
+    public function processAssert(
+        UrlRewrite $urlRewrite,
+        CatalogProductView $catalogProductView,
+        Browser $browser
+    ) {
+        $browser->open($_ENV['app_frontend_url'] . $urlRewrite->getRequestPath());
+        \PHPUnit_Framework_Assert::assertEquals(
+            $catalogProductView->getTitleBlock()->getTitle(),
+            $urlRewrite->getDataFieldConfig('product_id')['source']->getProduct()->getName(),
+            'URL rewrite product redirect false.'
+            . "\nExpected: " . $urlRewrite->getDataFieldConfig('product_id')['source']->getProduct()->getName()
+            . "\nActual: " . $catalogProductView->getTitleBlock()->getTitle()
+        );
+    }
+
+    /**
+     * Product available by new URL on the front
+     *
+     * @return string
+     */
+    public function toString()
+    {
+        return 'Product available by new URL on the front.';
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Constraint/AssertUrlRewriteCategoryRedirect.php b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Constraint/AssertUrlRewriteCategoryRedirect.php
index 3786499bc97..b82b58bd5cc 100644
--- a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Constraint/AssertUrlRewriteCategoryRedirect.php
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Constraint/AssertUrlRewriteCategoryRedirect.php
@@ -27,7 +27,7 @@ namespace Magento\UrlRewrite\Test\Constraint;
 use Mtf\Client\Browser;
 use Mtf\Constraint\AbstractConstraint;
 use Magento\UrlRewrite\Test\Fixture\UrlRewrite;
-use Magento\Catalog\Test\Fixture\CatalogCategoryEntity;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 
 /**
  * Class AssertUrlRewriteCategoryRedirect
@@ -46,24 +46,28 @@ class AssertUrlRewriteCategoryRedirect extends AbstractConstraint
      * Assert check URL rewrite category redirect
      *
      * @param UrlRewrite $urlRewrite
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @param Browser $browser
      * @return void
      */
     public function processAssert(
         UrlRewrite $urlRewrite,
-        CatalogCategoryEntity $category,
+        CatalogCategory $category,
         Browser $browser
     ) {
         $browser->open($_ENV['app_frontend_url'] . $urlRewrite->getRequestPath());
-        $url = strtolower($category->getName());
+        $url = $urlRewrite->getOptions() == 'No'
+            ? $urlRewrite->getRequestPath()
+            : strtolower($category->getName()) . '.html';
+
         \PHPUnit_Framework_Assert::assertEquals(
             $browser->getUrl(),
-            $_ENV['app_frontend_url'] . $url . '.html',
+            $_ENV['app_frontend_url'] . $url,
             'URL rewrite category redirect false.'
-            . "\nExpected: " . $_ENV['app_frontend_url'] . $url . '.html'
+            . "\nExpected: " . $_ENV['app_frontend_url'] . $url
             . "\nActual: " . $browser->getUrl()
         );
+
     }
 
     /**
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite.php b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite.php
index 9f84c5b500c..8ed995d48c5 100644
--- a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite.php
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite.php
@@ -56,6 +56,12 @@ class UrlRewrite extends InjectableFixture
         'backend_type' => 'virtual',
     ];
 
+    protected $product_id = [
+        'attribute_code' => 'product_id',
+        'backend_type' => 'virtual',
+        'source' => 'Magento\UrlRewrite\Test\Fixture\UrlRewrite\ProductId',
+    ];
+
     protected $store_id = [
         'attribute_code' => 'store_id',
         'backend_type' => 'varchar',
@@ -96,6 +102,11 @@ class UrlRewrite extends InjectableFixture
         return $this->getData('id_path');
     }
 
+    public function getProductId()
+    {
+        return $this->getData('product_id');
+    }
+
     public function getStoreId()
     {
         return $this->getData('store_id');
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite.xml b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite.xml
index 3e28df6a0c1..88247b3c1a8 100644
--- a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite.xml
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite.xml
@@ -38,12 +38,13 @@
             <attribute_code>id_path</attribute_code>
             <backend_type>virtual</backend_type>
         </id_path>
+        <product_id>
+            <attribute_code>product_id</attribute_code>
+            <backend_type>virtual</backend_type>
+        </product_id>
         <store_id>
             <attribute_code>store_id</attribute_code>
-            <backend_type>varchar</backend_type>
-            <is_required>1</is_required>
-            <default_value>Default Store View</default_value>
-            <input>select</input>
+            <backend_type>virtual</backend_type>
         </store_id>
         <options>
             <attribute_code>options</attribute_code>
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite/ProductId.php b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite/ProductId.php
new file mode 100644
index 00000000000..17c31ee4ab9
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Fixture/UrlRewrite/ProductId.php
@@ -0,0 +1,109 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\UrlRewrite\Test\Fixture\UrlRewrite;
+
+use Mtf\Fixture\FixtureFactory;
+use Mtf\Fixture\FixtureInterface;
+
+/**
+ * Class ProductId
+ * Prepare product
+ */
+class ProductId implements FixtureInterface
+{
+    /**
+     * Resource data
+     *
+     * @var string
+     */
+    protected $data;
+
+    /**
+     * Return product
+     *
+     * @var FixtureInterface
+     */
+    protected $product;
+
+    /**
+     * @param FixtureFactory $fixtureFactory
+     * @param array $params
+     * @param array $data
+     */
+    public function __construct(FixtureFactory $fixtureFactory, array $params, array $data = [])
+    {
+        $this->params = $params;
+        $explodeValue = explode('::', $data['dataSet']);
+        if (!empty($explodeValue) && count($explodeValue) > 1) {
+            /** @var FixtureInterface $fixture */
+            $this->product = $fixtureFactory->createByCode($explodeValue[0], ['dataSet' => $explodeValue[1]]);
+            $this->product->persist();
+            $this->data =  $this->product->getId();
+        } else {
+            $this->data = strval($data['dataSet']);
+        }
+    }
+
+    /**
+     * Persist custom selections products
+     *
+     * @return void
+     */
+    public function persist()
+    {
+        //
+    }
+
+    /**
+     * Return prepared data
+     *
+     * @param string|null $key
+     * @return string
+     */
+    public function getData($key = null)
+    {
+        return $this->data;
+    }
+
+    /**
+     * Return data set configuration settings
+     *
+     * @return array
+     */
+    public function getDataConfig()
+    {
+        return $this->params;
+    }
+
+    /**
+     * Return product
+     *
+     * @return FixtureInterface
+     */
+    public function getProduct()
+    {
+        return $this->product;
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Handler/UrlRewrite/Curl.php b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Handler/UrlRewrite/Curl.php
index 49368c86669..b34e502aac8 100644
--- a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Handler/UrlRewrite/Curl.php
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Handler/UrlRewrite/Curl.php
@@ -67,7 +67,7 @@ class Curl extends AbstractCurl implements UrlRewriteInterface
      */
     public function persist(FixtureInterface $fixture = null)
     {
-        $url = $_ENV['app_backend_url'] . $this->url . $fixture->getData('id_path');
+        $url = $_ENV['app_backend_url'] . $this->url . $fixture->getIdPath();
         $data = $this->prepareData($fixture->getData());
         $curl = new BackendDecorator(new CurlTransport(), new Config());
         $curl->write(CurlInterface::POST, $url, '1.0', array(), $data);
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Repository/UrlRewrite.php b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Repository/UrlRewrite.php
index 743f2fe3af7..0d461528f1a 100644
--- a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Repository/UrlRewrite.php
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/Repository/UrlRewrite.php
@@ -40,7 +40,7 @@ class UrlRewrite extends AbstractRepository
     {
         $this->_data['default'] = [
             'request_path' => 'test-test-test%isolation%.html',
-            'options' => 'No',
+            'options' => 'Temporary (302)',
             'store_id' => 'Default Store View'
         ];
     }
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/CreateCategoryRewritesEntityTest.php b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/CreateCategoryRewriteEntityTest.php
similarity index 90%
rename from dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/CreateCategoryRewritesEntityTest.php
rename to dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/CreateCategoryRewriteEntityTest.php
index 0fdc0cffdd4..d3a7cc9de79 100644
--- a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/CreateCategoryRewritesEntityTest.php
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/CreateCategoryRewriteEntityTest.php
@@ -28,7 +28,7 @@ use Magento\UrlRewrite\Test\Fixture\UrlRewrite;
 use Magento\UrlRewrite\Test\Page\Adminhtml\UrlrewriteEdit;
 use Magento\UrlRewrite\Test\Page\Adminhtml\UrlrewriteIndex;
 use Mtf\Fixture\FixtureFactory;
-use Magento\Catalog\Test\Fixture\CatalogCategoryEntity;
+use Magento\Catalog\Test\Fixture\CatalogCategory;
 use Mtf\TestCase\Injectable;
 
 /**
@@ -50,7 +50,7 @@ use Mtf\TestCase\Injectable;
  * @group URL_Rewrites_(MX)
  * @ZephyrId MAGETWO-24280
  */
-class CreateCategoryRewritesEntityTest extends Injectable
+class CreateCategoryRewriteEntityTest extends Injectable
 {
     /**
      * Page of url rewrite edit category
@@ -82,7 +82,7 @@ class CreateCategoryRewritesEntityTest extends Injectable
         $this->urlRewriteEdit = $urlRewriteEdit;
         $this->urlRewriteIndex = $urlRewriteIndex;
         $category = $fixtureFactory->createByCode(
-            'catalogCategoryEntity',
+            'catalogCategory',
             ['dataSet' => 'default_subcategory']
         );
         $category->persist();
@@ -93,10 +93,10 @@ class CreateCategoryRewritesEntityTest extends Injectable
      * Test check create category rewrites
      *
      * @param UrlRewrite $urlRewrite
-     * @param CatalogCategoryEntity $category
+     * @param CatalogCategory $category
      * @return void
      */
-    public function testCreateCategoryRewrites(UrlRewrite $urlRewrite, CatalogCategoryEntity $category)
+    public function testCreateCategoryRewrite(UrlRewrite $urlRewrite, CatalogCategory $category)
     {
         //Steps
         $this->urlRewriteIndex->open();
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/CreateCategoryRewritesEntityTest/testCreateCategoryRewrites.csv b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/CreateCategoryRewriteEntityTest/testCreateCategoryRewrite.csv
similarity index 100%
rename from dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/CreateCategoryRewritesEntityTest/testCreateCategoryRewrites.csv
rename to dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/CreateCategoryRewriteEntityTest/testCreateCategoryRewrite.csv
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/DeleteProductUrlRewritesEntityTest.php b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/DeleteProductUrlRewriteEntityTest.php
similarity index 96%
rename from dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/DeleteProductUrlRewritesEntityTest.php
rename to dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/DeleteProductUrlRewriteEntityTest.php
index f1a7b36911d..6b7b8baa82b 100644
--- a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/DeleteProductUrlRewritesEntityTest.php
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/DeleteProductUrlRewriteEntityTest.php
@@ -49,7 +49,7 @@ use Mtf\TestCase\Injectable;
  * @group URL_Rewrites_(PS)
  * @ZephyrId  MAGETWO-23287
  */
-class DeleteProductUrlRewritesEntityTest extends Injectable
+class DeleteProductUrlRewriteEntityTest extends Injectable
 {
     /**
      * Url rewrite index page
@@ -103,7 +103,7 @@ class DeleteProductUrlRewritesEntityTest extends Injectable
      * @param UrlRewrite $productRedirect
      * @return void
      */
-    public function testDeleteProductUrlRewrites(UrlRewrite $productRedirect)
+    public function testDeleteProductUrlRewrite(UrlRewrite $productRedirect)
     {
         $this->urlRewriteIndex->open();
         $filter = ['request_path' => $productRedirect->getRequestPath()];
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/DeleteProductUrlRewritesEntityTest/testDeleteProductUrlRewrites.csv b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/DeleteProductUrlRewriteEntityTest/testDeleteProductUrlRewrite.csv
similarity index 100%
rename from dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/DeleteProductUrlRewritesEntityTest/testDeleteProductUrlRewrites.csv
rename to dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/DeleteProductUrlRewriteEntityTest/testDeleteProductUrlRewrite.csv
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateCategoryUrlRewriteEntityTest.php b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateCategoryUrlRewriteEntityTest.php
new file mode 100644
index 00000000000..f27c54428de
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateCategoryUrlRewriteEntityTest.php
@@ -0,0 +1,116 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\UrlRewrite\Test\TestCase;
+
+use Magento\Catalog\Test\Fixture\CatalogCategory;
+use Mtf\TestCase\Injectable;
+use Magento\UrlRewrite\Test\Page\Adminhtml\UrlrewriteIndex;
+use Magento\UrlRewrite\Test\Page\Adminhtml\UrlrewriteEdit;
+use Mtf\Fixture\FixtureFactory;
+use Magento\UrlRewrite\Test\Fixture\UrlRewrite;
+
+/**
+ * Test Creation for UpdateCategoryUrlRewritesEntity
+ *
+ * Test Flow:
+ *
+ * Precondition:
+ * 1. SubCategory is created.
+ * 2. Category URL Rewrite is created.
+ *
+ * Steps:
+ * 1. Log in to backend as Admin.
+ * 2. Go to the Marketing-> SEO & Search->URL Redirects.
+ * 3. Click Category URL Rewrite from grid.
+ * 4. Edit test value(s) according to dataSet.
+ * 5. Click 'Save' button.
+ * 6. Perform all asserts.
+ *
+ * @group URL_Rewrites_(PS)
+ * @ZephyrId MAGETWO-24838
+ */
+class UpdateCategoryUrlRewriteEntityTest extends Injectable
+{
+    /**
+     * Url rewrite index page
+     *
+     * @var UrlrewriteIndex
+     */
+    protected $urlRewriteIndex;
+
+    /**
+     * Url rewrite edit page
+     *
+     * @var UrlrewriteEdit
+     */
+    protected $urlRewriteEdit;
+
+    /**
+     * Prepare dataSets and pages
+     *
+     * @param UrlrewriteIndex $urlRewriteIndex
+     * @param UrlrewriteEdit $urlRewriteEdit
+     * @param FixtureFactory $fixtureFactory
+     * @param CatalogCategory $category
+     * @return array
+     */
+    public function __inject(
+        UrlrewriteIndex $urlRewriteIndex,
+        UrlrewriteEdit $urlRewriteEdit,
+        FixtureFactory $fixtureFactory,
+        CatalogCategory $category
+    ) {
+        $this->urlRewriteIndex = $urlRewriteIndex;
+        $this->urlRewriteEdit = $urlRewriteEdit;
+        $category->persist();
+        $categoryRedirect = $fixtureFactory->createByCode(
+            'urlRewrite',
+            [
+                'dataSet' => 'default',
+                'data' => ['id_path' => 'category/' . $category->getId()]
+            ]
+        );
+        $categoryRedirect->persist();
+
+        return ['categoryRedirect' => $categoryRedirect, 'category' => $category];
+    }
+
+    /**
+     * Update category URL rewrites
+     *
+     * @param UrlRewrite $categoryRedirect
+     * @param UrlRewrite $urlRewrite
+     * @return void
+     */
+    public function testUpdateCategoryUrlRewrite(UrlRewrite $categoryRedirect, UrlRewrite $urlRewrite)
+    {
+        //Steps
+        $this->urlRewriteIndex->open();
+        $filter = ['request_path' => $categoryRedirect->getRequestPath()];
+        $this->urlRewriteIndex->getUrlRedirectGrid()->searchAndOpen($filter);
+        $this->urlRewriteEdit->getFormBlock()->fill($urlRewrite);
+        $this->urlRewriteEdit->getPageMainActions()->save();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateCategoryUrlRewriteEntityTest/testUpdateCategoryUrlRewrite.csv b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateCategoryUrlRewriteEntityTest/testUpdateCategoryUrlRewrite.csv
new file mode 100644
index 00000000000..9b8902a40dc
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateCategoryUrlRewriteEntityTest/testUpdateCategoryUrlRewrite.csv
@@ -0,0 +1,5 @@
+"category/dataSet";"categoryRewrite/dataSet";"urlRewrite/data/store_id";"urlRewrite/data/request_path";"urlRewrite/data/options";"urlRewrite/data/description";"constraint"
+"default_subcategory";"default";"-";"test_request%isolation%";"No";"test_description_defalt";"assertUrlRewriteSaveMessage, assertUrlRewriteInGrid, assertUrlRewriteCategoryRedirect"
+"default_subcategory";"default";"-";"request_path%isolation%.html";"Temporary (302)";"test description_302";"assertUrlRewriteSaveMessage, assertUrlRewriteInGrid, assertUrlRewriteCategoryRedirect"
+"default_subcategory";"default";"-";"request_path%isolation%.htm";"Permanent (301)";"test description_301";"assertUrlRewriteSaveMessage, assertUrlRewriteInGrid, assertUrlRewriteCategoryRedirect"
+"default_subcategory";"default";"-";"request_path%isolation%.aspx";"Temporary (302)";"test description_%isolation%";"assertUrlRewriteSaveMessage, assertUrlRewriteInGrid, assertUrlRewriteCategoryRedirect"
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateProductUrlRewriteEntityTest.php b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateProductUrlRewriteEntityTest.php
new file mode 100644
index 00000000000..88e91acf55c
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateProductUrlRewriteEntityTest.php
@@ -0,0 +1,111 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\UrlRewrite\Test\TestCase;
+
+use Mtf\TestCase\Injectable;
+use Magento\UrlRewrite\Test\Fixture\UrlRewrite;
+use Magento\UrlRewrite\Test\Page\Adminhtml\UrlrewriteIndex;
+use Magento\UrlRewrite\Test\Page\Adminhtml\UrlrewriteEdit;
+use Mtf\Fixture\FixtureFactory;
+
+/**
+ * Test Creation for Update Product URL Rewrites Entity
+ *
+ * Test Flow:
+ *
+ * Preconditions:
+ * 1. Create custom store view
+ * 2. Create simple product
+ * 3. Create product UrlRewrite
+ *
+ * Steps:
+ * 1. Open Backend
+ * 2. Go to Marketing->Url Redirects
+ * 3. Search and open created Url Redirect
+ * 4. Fill data according to dataset
+ * 5. Perform all assertions
+ *
+ * @group URL_Rewrites_(PS)
+ * @ZephyrId MAGETWO-24819
+ */
+class UpdateProductUrlRewriteEntityTest extends Injectable
+{
+    /**
+     * Url rewrite index page
+     *
+     * @var UrlrewriteIndex
+     */
+    protected $urlRewriteIndex;
+
+    /**
+     * Url rewrite edit page
+     *
+     * @var UrlrewriteEdit
+     */
+    protected $urlRewriteEdit;
+
+    /**
+     * Prepare dataSets and pages
+     *
+     * @param UrlrewriteIndex $urlRewriteIndex
+     * @param UrlrewriteEdit $urlRewriteEdit
+     * @return array
+     */
+    public function __inject(
+        UrlrewriteIndex $urlRewriteIndex,
+        UrlrewriteEdit $urlRewriteEdit
+    ) {
+        $this->urlRewriteIndex = $urlRewriteIndex;
+        $this->urlRewriteEdit = $urlRewriteEdit;
+    }
+
+    /**
+     * Update product URL rewrites
+     *
+     * @param UrlRewrite $urlRewrite
+     * @param FixtureFactory $fixtureFactory
+     * @return void
+     */
+    public function testUpdateProductUrlRewrite(
+        UrlRewrite $urlRewrite,
+        FixtureFactory $fixtureFactory
+    ) {
+        /** @var UrlRewrite $productRedirect */
+        $productRedirect = $fixtureFactory->createByCode(
+            'urlRewrite',
+            [
+                'dataSet' => 'default',
+                'data' => ['id_path' => 'product/' . $urlRewrite->getProductId()]
+            ]
+        );
+        $productRedirect->persist();
+        //Steps
+        $this->urlRewriteIndex->open();
+        $filter = ['request_path' => $productRedirect->getRequestPath()];
+        $this->urlRewriteIndex->getUrlRedirectGrid()->searchAndOpen($filter);
+        $this->urlRewriteEdit->getFormBlock()->fill($urlRewrite);
+        $this->urlRewriteEdit->getPageMainActions()->save();
+    }
+}
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateProductUrlRewriteEntityTest/testUpdateProductUrlRewrite.csv b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateProductUrlRewriteEntityTest/testUpdateProductUrlRewrite.csv
new file mode 100644
index 00000000000..a2149c6d1a8
--- /dev/null
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/TestCase/UpdateProductUrlRewriteEntityTest/testUpdateProductUrlRewrite.csv
@@ -0,0 +1,3 @@
+"urlRewrite/data/product_id/dataSet";"urlRewrite/data/store_id";"urlRewrite/data/request_path";"urlRewrite/data/options";"urlRewrite/data/description";"isRequired";"constraint"
+"catalogProductSimple::100_dollar_product";"Main Website/Main Website Store/Default Store View";"test_%isolation%.html";"Temporary (302)";"description_%isolation%";"Yes";"assertUrlRewriteSaveMessage, assertProductUrlAvailableOnTheFront"
+"catalogProductSimple::100_dollar_product";"Main Website/Main Website Store/Custom Store View";"test_%isolation%.php";"No";"description_%isolation%";"No";"assertUrlRewriteSaveMessage, assertProductUrlAvailableOnTheFront"
\ No newline at end of file
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/etc/curl/di.xml b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/etc/curl/di.xml
index 6dcbbc44a53..d91a6b64486 100644
--- a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/etc/curl/di.xml
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/etc/curl/di.xml
@@ -23,6 +23,6 @@
  * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
  */
 -->
-<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../../../../lib/Magento/Framework/ObjectManager/etc/config.xsd">
+<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../../../../lib/internal/Magento/Framework/ObjectManager/etc/config.xsd">
     <preference for="\Magento\UrlRewrite\Test\Handler\UrlRewrite\UrlRewriteInterface" type="\Magento\UrlRewrite\Test\Handler\UrlRewrite\Curl" />
 </config>
diff --git a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/etc/global/constraint.xml b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/etc/global/constraint.xml
index a31770c3011..60b2f162099 100644
--- a/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/etc/global/constraint.xml
+++ b/dev/tests/functional/tests/app/Magento/UrlRewrite/Test/etc/global/constraint.xml
@@ -37,6 +37,15 @@
     <assertUrlRewriteCategoryRedirect module="Magento_UrlRewrite">
         <severeness>low</severeness>
     </assertUrlRewriteCategoryRedirect>
+    <assertProductUrlAvailableOnTheFront module="Magento_UrlRewrite">
+        <severeness>low</severeness>
+        <require>
+            <urlRewrite class="Magento\UrlRewrite\Test\Fixture\UrlRewrite"/>
+            <catalogProductView class="Magento\Catalog\Test\Page\Product\CatalogProductView"/>
+            <product class="Mtf\Fixture\FixtureInterface"/>
+            <browser class="Mtf\Client\Browser"/>
+        </require>
+    </assertProductUrlAvailableOnTheFront>
     <assertUrlRewriteDeletedMessage module="Magento_UrlRewrite">
         <severeness>low</severeness>
         <require>
diff --git a/dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/Edit.php b/dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/RoleForm.php
similarity index 95%
rename from dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/Edit.php
rename to dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/RoleForm.php
index 46e6b55a578..8667fe8c7f2 100644
--- a/dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/Edit.php
+++ b/dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/RoleForm.php
@@ -27,10 +27,10 @@ namespace Magento\User\Test\Block\Adminhtml\Role;
 use Magento\Backend\Test\Block\Widget\FormTabs;
 
 /**
- * Class Edit
+ * Class RoleForm
  * Role edit form page
  */
-class Edit extends FormTabs
+class RoleForm extends FormTabs
 {
     //
 }
diff --git a/dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/Edit.xml b/dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/RoleForm.xml
similarity index 100%
rename from dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/Edit.xml
rename to dev/tests/functional/tests/app/Magento/User/Test/Block/Adminhtml/Role/RoleForm.xml
diff --git a/dev/tests/functional/tests/app/Magento/User/Test/Page/Adminhtml/UserRoleEditRole.php b/dev/tests/functional/tests/app/Magento/User/Test/Page/Adminhtml/UserRoleEditRole.php
index bf2b2b958b9..b9f795d4189 100644
--- a/dev/tests/functional/tests/app/Magento/User/Test/Page/Adminhtml/UserRoleEditRole.php
+++ b/dev/tests/functional/tests/app/Magento/User/Test/Page/Adminhtml/UserRoleEditRole.php
@@ -42,7 +42,7 @@ class UserRoleEditRole extends BackendPage
         ],
         'roleFormTabs' => [
             'name' => 'roleFormTabs',
-            'class' => 'Magento\User\Test\Block\Adminhtml\Role\Edit',
+            'class' => 'Magento\User\Test\Block\Adminhtml\Role\RoleForm',
             'locator' => '[id="page:main-container"]',
             'strategy' => 'css selector',
         ],
@@ -63,7 +63,7 @@ class UserRoleEditRole extends BackendPage
     }
 
     /**
-     * @return \Magento\User\Test\Block\Adminhtml\Role\Edit
+     * @return \Magento\User\Test\Block\Adminhtml\Role\RoleForm
      */
     public function getRoleFormTabs()
     {
diff --git a/dev/tests/functional/tests/app/Magento/User/Test/Page/Adminhtml/UserRoleEditRole.xml b/dev/tests/functional/tests/app/Magento/User/Test/Page/Adminhtml/UserRoleEditRole.xml
index a4c60f63b0d..e2f95c78ff8 100644
--- a/dev/tests/functional/tests/app/Magento/User/Test/Page/Adminhtml/UserRoleEditRole.xml
+++ b/dev/tests/functional/tests/app/Magento/User/Test/Page/Adminhtml/UserRoleEditRole.xml
@@ -32,7 +32,7 @@
     </block>
     <block>
         <name>roleFormTabs</name>
-        <class>Magento\User\Test\Block\Adminhtml\Role\Edit</class>
+        <class>Magento\User\Test\Block\Adminhtml\Role\RoleForm</class>
         <locator>[id="page:main-container"]</locator>
         <strategy>css selector</strategy>
     </block>
diff --git a/dev/tests/functional/tests/app/Magento/User/Test/etc/curl/di.xml b/dev/tests/functional/tests/app/Magento/User/Test/etc/curl/di.xml
index 60f06e7f111..75b2f2086ca 100644
--- a/dev/tests/functional/tests/app/Magento/User/Test/etc/curl/di.xml
+++ b/dev/tests/functional/tests/app/Magento/User/Test/etc/curl/di.xml
@@ -23,7 +23,7 @@
  * @license     http://opensource.org/licenses/afl-3.0.php  Academic Free License (AFL 3.0)
  */
 -->
-<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../../../../lib/Magento/Framework/ObjectManager/etc/config.xsd">
+<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../../../../../lib/internal/Magento/Framework/ObjectManager/etc/config.xsd">
     <preference for="Magento\User\Test\Handler\AdminUserRole\AdminUserRoleInterface" type="\Magento\User\Test\Handler\AdminUserRole\Curl"/>
     <preference for="Magento\User\Test\Handler\AdminUser\AdminUserInterface" type="\Magento\User\Test\Handler\AdminUser\Curl"/>
 </config>
\ No newline at end of file
diff --git a/dev/tests/integration/framework/Magento/TestFramework/Bootstrap.php b/dev/tests/integration/framework/Magento/TestFramework/Bootstrap.php
index 65345af1311..da44770f85f 100644
--- a/dev/tests/integration/framework/Magento/TestFramework/Bootstrap.php
+++ b/dev/tests/integration/framework/Magento/TestFramework/Bootstrap.php
@@ -51,6 +51,11 @@ class Bootstrap
      */
     private $_dbVendorName;
 
+    /**
+     * @var \Magento\Framework\Simplexml\Element
+     */
+    private $dbConfig;
+
     /**
      * @var \Magento\TestFramework\Application
      */
@@ -138,6 +143,16 @@ class Bootstrap
         return $this->_dbVendorName;
     }
 
+    /**
+     * Retrieve the database configuration
+     *
+     * @return \Magento\Framework\Simplexml\Element
+     */
+    public function getDbConfig()
+    {
+        return $this->dbConfig;
+    }
+
     /**
      * Perform bootstrap actions required to completely setup the testing environment
      */
@@ -210,17 +225,17 @@ class Bootstrap
         $appMode
     ) {
         $localConfigXml = $this->_loadConfigFiles($localConfigFiles);
-        $dbConfig = $localConfigXml->connection;
-        $this->_dbVendorName = $this->_determineDbVendorName($dbConfig);
+        $this->dbConfig = $localConfigXml->connection;
+        $this->_dbVendorName = $this->_determineDbVendorName($this->dbConfig);
         $sandboxUniqueId = $this->_calcConfigFilesHash($localConfigFiles);
         $installDir = "{$this->_tmpDir}/sandbox-{$this->_dbVendorName}-{$sandboxUniqueId}";
         $dbClass = 'Magento\TestFramework\Db\\' . ucfirst($this->_dbVendorName);
         /** @var $dbInstance \Magento\TestFramework\Db\AbstractDb */
         $dbInstance = new $dbClass(
-            (string)$dbConfig->host,
-            (string)$dbConfig->username,
-            (string)$dbConfig->password,
-            (string)$dbConfig->dbName,
+            (string)$this->dbConfig->host,
+            (string)$this->dbConfig->username,
+            (string)$this->dbConfig->password,
+            (string)$this->dbConfig->dbName,
             $this->_tmpDir,
             $this->_shell
         );
diff --git a/dev/tests/integration/phpunit.xml.dist b/dev/tests/integration/phpunit.xml.dist
index 540df596a54..51962f3c709 100644
--- a/dev/tests/integration/phpunit.xml.dist
+++ b/dev/tests/integration/phpunit.xml.dist
@@ -63,6 +63,8 @@
         <!-- Memory usage and estimated leaks thresholds -->
         <!--<const name="TESTS_MEM_USAGE_LIMIT" value="1024M"/>-->
         <const name="TESTS_MEM_LEAK_LIMIT" value=""/>
+        <!-- Path to Percona Toolkit bin directory -->
+        <!--<const name="PERCONA_TOOLKIT_BIN_DIR" value=""/>-->
         <!-- CSV Profiler Output file -->
         <!--<const name="TESTS_PROFILER_FILE" value="profiler.csv"/>-->
         <!-- Bamboo compatible CSV Profiler Output file name -->
diff --git a/dev/tests/integration/testsuite/Magento/Catalog/Model/CategoryTest.php b/dev/tests/integration/testsuite/Magento/Catalog/Model/CategoryTest.php
index 2dd109129c7..3e30cf4c7b4 100644
--- a/dev/tests/integration/testsuite/Magento/Catalog/Model/CategoryTest.php
+++ b/dev/tests/integration/testsuite/Magento/Catalog/Model/CategoryTest.php
@@ -293,6 +293,11 @@ class CategoryTest extends \PHPUnit_Framework_TestCase
 
     public function testValidate()
     {
+        $this->_model->addData(array(
+            "include_in_menu" => false,
+            "is_active" => false,
+            'name' => 'test'
+        ));
         $this->assertNotEmpty($this->_model->validate());
     }
 }
diff --git a/dev/tests/integration/testsuite/Magento/CatalogInventory/Model/Config/Backend/ManagestockTest.php b/dev/tests/integration/testsuite/Magento/CatalogInventory/Model/Config/Backend/ManagestockTest.php
new file mode 100644
index 00000000000..6ffc20b9755
--- /dev/null
+++ b/dev/tests/integration/testsuite/Magento/CatalogInventory/Model/Config/Backend/ManagestockTest.php
@@ -0,0 +1,89 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogInventory\Model\Config\Backend;
+
+use Magento\TestFramework\Helper\Bootstrap as Bootstrap;
+
+/**
+ * Class ManagestockTest
+ */
+class ManagestockTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * Data provider for testSaveAndRebuildIndex
+     * @return array
+     */
+    public function saveAndRebuildIndexDataProvider()
+    {
+        return [
+            [1, 1],
+            [0, 0],
+        ];
+    }
+
+    /**
+     * Test rebuild stock indexer on stock status config save
+     *
+     * @dataProvider saveAndRebuildIndexDataProvider
+     *
+     * @magentoAppIsolation enabled
+     * @magentoDbIsolation enabled
+     * @magentoConfigFixture default/cataloginventory/item_options/manage_stock 0
+     *
+     * @param int $newStockValue new value for stock status
+     * @param int $callCount count matcher
+     */
+    public function testSaveAndRebuildIndex($newStockValue, $callCount)
+    {
+        /** @var \Magento\CatalogInventory\Model\Stock\Status */
+        $stockStatus = $this->getMock(
+            '\Magento\CatalogInventory\Model\Stock\Status',
+            ['rebuild'],
+            [],
+            '',
+            false
+        );
+
+        $stockStatus->expects($this->exactly($callCount))
+            ->method('rebuild')
+            ->will($this->returnValue($stockStatus));
+
+        $manageStock = new Managestock(
+            Bootstrap::getObjectManager()->get('\Magento\Framework\Model\Context'),
+            Bootstrap::getObjectManager()->get('\Magento\Framework\Registry'),
+            Bootstrap::getObjectManager()->get('\Magento\Framework\App\Config\ScopeConfigInterface'),
+            $stockStatus,
+            Bootstrap::getObjectManager()->get('Magento\Core\Model\Resource\Config')
+        );
+
+        $manageStock->setPath('cataloginventory/item_options/manage_stock')
+            ->setScope('default')
+            ->setScopeId(0);
+
+        $manageStock->setValue($newStockValue);
+
+        // assert
+        $manageStock->save();
+    }
+}
diff --git a/dev/tests/integration/testsuite/Magento/CatalogInventory/Model/Stock/ItemTest.php b/dev/tests/integration/testsuite/Magento/CatalogInventory/Model/Stock/ItemTest.php
index 087456ebfee..b2d3f3f420e 100644
--- a/dev/tests/integration/testsuite/Magento/CatalogInventory/Model/Stock/ItemTest.php
+++ b/dev/tests/integration/testsuite/Magento/CatalogInventory/Model/Stock/ItemTest.php
@@ -46,23 +46,15 @@ class ItemTest extends \PHPUnit_Framework_TestCase
         $product = \Magento\TestFramework\Helper\Bootstrap::getObjectManager()->create(
             'Magento\Catalog\Model\Product'
         );
-        $product->setTypeId(
-            'simple'
-        )->setId(
-            1
-        )->setAttributeSetId(
-            4
-        )->setName(
-            'Simple Product'
-        )->setSku(
-            'simple'
-        )->setPrice(
-            10
-        )->setVisibility(
-            \Magento\Catalog\Model\Product\Visibility::VISIBILITY_BOTH
-        )->setStatus(
-            \Magento\Catalog\Model\Product\Attribute\Source\Status::STATUS_ENABLED
-        )->save();
+        $product->setTypeId('simple')
+            ->setId(1)
+            ->setAttributeSetId(4)
+            ->setName('Simple Product')
+            ->setSku('simple')
+            ->setPrice(10)
+            ->setVisibility(\Magento\Catalog\Model\Product\Visibility::VISIBILITY_BOTH)
+            ->setStatus(\Magento\Catalog\Model\Product\Attribute\Source\Status::STATUS_ENABLED)
+            ->save();
     }
 
     /**
@@ -70,15 +62,10 @@ class ItemTest extends \PHPUnit_Framework_TestCase
      */
     public function testSaveWithNullQty()
     {
-        $this->_model->setProductId(
-            1
-        )->setTypeId(
-            \Magento\Catalog\Model\Product\Type::DEFAULT_TYPE
-        )->setStockId(
-            \Magento\CatalogInventory\Model\Stock::DEFAULT_STOCK_ID
-        )->setQty(
-            null
-        );
+        $this->_model->setProductId(1)
+            ->setTypeId(\Magento\Catalog\Model\Product\Type::DEFAULT_TYPE)
+            ->setStockId(\Magento\CatalogInventory\Model\Stock::DEFAULT_STOCK_ID)
+            ->setQty(null);
         $this->_model->save();
 
         $this->_model->setQty(2);
@@ -99,15 +86,10 @@ class ItemTest extends \PHPUnit_Framework_TestCase
      */
     public function testStockStatusChangedAuto()
     {
-        $this->_model->setProductId(
-            1
-        )->setTypeId(
-            \Magento\Catalog\Model\Product\Type::DEFAULT_TYPE
-        )->setStockId(
-            \Magento\CatalogInventory\Model\Stock::DEFAULT_STOCK_ID
-        )->setQty(
-            1
-        );
+        $this->_model->setProductId(1)
+            ->setTypeId(\Magento\Catalog\Model\Product\Type::DEFAULT_TYPE)
+            ->setStockId(\Magento\CatalogInventory\Model\Stock::DEFAULT_STOCK_ID)
+            ->setQty(1);
         $this->_model->save();
         $this->assertEquals(0, $this->_model->getStockStatusChangedAuto());
 
@@ -126,16 +108,4 @@ class ItemTest extends \PHPUnit_Framework_TestCase
         $this->_model->setUseConfigEnableQtyInc(true);
         $this->assertTrue($this->_model->getEnableQtyIncrements());
     }
-
-    public function testSetGetProduct()
-    {
-        $this->assertNull($this->_model->getProduct());
-        $productOne = new \Magento\Framework\Object();
-        $this->_model->setData('product', $productOne);
-        $this->assertSame($productOne, $this->_model->getProduct());
-
-        $productTwo = new \Magento\Framework\Object();
-        $this->_model->setProduct($productTwo);
-        $this->assertSame($productTwo, $this->_model->getProduct());
-    }
 }
diff --git a/dev/tests/integration/testsuite/Magento/DatabaseTest.php b/dev/tests/integration/testsuite/Magento/DatabaseTest.php
new file mode 100644
index 00000000000..edbefd3aeae
--- /dev/null
+++ b/dev/tests/integration/testsuite/Magento/DatabaseTest.php
@@ -0,0 +1,51 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento;
+
+use Magento\TestFramework\Helper\Bootstrap;
+
+class DatabaseTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * Assure that there are no redundant indexes declared in database
+     */
+    public function testDuplicateKeys()
+    {
+        if (!defined('PERCONA_TOOLKIT_BIN_DIR')) {
+            $this->markTestSkipped('Path to Percona Toolkit is not specified.');
+        }
+        $checkerPath = PERCONA_TOOLKIT_BIN_DIR . '/pt-duplicate-key-checker';
+
+        $dbConfig = Bootstrap::getInstance()->getBootstrap()->getDbConfig();
+        $command = $checkerPath . ' -d ' . $dbConfig->dbName
+            . ' h=' . $dbConfig->host . ',u=' . $dbConfig->username . ',p=' . $dbConfig->password;
+
+        exec($command, $output, $exitCode);
+        $this->assertEquals(0, $exitCode);
+        $output = implode(PHP_EOL, $output);
+        if (preg_match('/Total Duplicate Indexes\s+(\d+)/', $output, $matches)) {
+            $this->fail($matches[1] . ' duplicate indexes found.' . PHP_EOL . PHP_EOL . $output);
+        }
+    }
+}
diff --git a/dev/tests/integration/testsuite/Magento/Eav/Model/Validator/Attribute/BackendTest.php b/dev/tests/integration/testsuite/Magento/Eav/Model/Validator/Attribute/BackendTest.php
index 8c5b5607c9b..7481a7f1078 100644
--- a/dev/tests/integration/testsuite/Magento/Eav/Model/Validator/Attribute/BackendTest.php
+++ b/dev/tests/integration/testsuite/Magento/Eav/Model/Validator/Attribute/BackendTest.php
@@ -60,9 +60,9 @@ class BackendTest extends \PHPUnit_Framework_TestCase
         $this->assertFalse($this->_model->isValid($entity));
         $this->assertArrayHasKey('email', $this->_model->getMessages());
 
-        $entity->setData('store_id', null);
+        $entity->setData('firstname', null);
         $this->assertFalse($this->_model->isValid($entity));
         $this->assertArrayHasKey('email', $this->_model->getMessages());
-        $this->assertArrayHasKey('store_id', $this->_model->getMessages());
+        $this->assertArrayHasKey('firstname', $this->_model->getMessages());
     }
 }
diff --git a/dev/tests/integration/testsuite/Magento/Sales/Controller/Adminhtml/Order/CreditmemoTest.php b/dev/tests/integration/testsuite/Magento/Sales/Controller/Adminhtml/Order/CreditmemoTest.php
index e6dfa5d300b..b1e58b0200e 100644
--- a/dev/tests/integration/testsuite/Magento/Sales/Controller/Adminhtml/Order/CreditmemoTest.php
+++ b/dev/tests/integration/testsuite/Magento/Sales/Controller/Adminhtml/Order/CreditmemoTest.php
@@ -34,16 +34,18 @@ class CreditmemoTest extends \Magento\Backend\Utility\Controller
      */
     public function testAddCommentAction()
     {
-        /** @var $stockItem \Magento\CatalogInventory\Model\Stock\Item */
-        $stockItem = \Magento\TestFramework\Helper\Bootstrap::getObjectManager()->create(
-            'Magento\CatalogInventory\Model\Stock\Item'
-        );
+        $objectManager = \Magento\TestFramework\Helper\Bootstrap::getObjectManager();
+        /** @var \Magento\CatalogInventory\Model\Stock\Status $status */
+        $status = $objectManager->get('Magento\CatalogInventory\Model\Stock\Status');
+        $status->updateStatus(1);
+        /** @var \Magento\CatalogInventory\Model\Stock\Item $stockItem */
+        $stockItem = $objectManager->create('Magento\CatalogInventory\Model\Stock\Item');
         $stockItem->loadByProduct(1);
         $this->assertEquals(95, $stockItem->getStockQty());
         $stockItem = null;
 
-        /** @var $order \Magento\Sales\Model\Order */
-        $order = \Magento\TestFramework\Helper\Bootstrap::getObjectManager()->create('Magento\Sales\Model\Order');
+        /** @var \Magento\Sales\Model\Order $order */
+        $order = $objectManager->create('Magento\Sales\Model\Order');
         $order->load('100000001', 'increment_id');
 
         $items = $order->getCreditmemosCollection()->getItems();
@@ -57,10 +59,8 @@ class CreditmemoTest extends \Magento\Backend\Utility\Controller
         $html = $this->getResponse()->getBody();
 
         $this->assertContains($comment, $html);
-        /** @var $stockItem \Magento\CatalogInventory\Model\Stock\Item */
-        $stockItem = \Magento\TestFramework\Helper\Bootstrap::getObjectManager()->create(
-            'Magento\CatalogInventory\Model\Stock\Item'
-        );
+        /** @var \Magento\CatalogInventory\Model\Stock\Item $stockItem */
+        $stockItem = $objectManager->create('Magento\CatalogInventory\Model\Stock\Item');
         $stockItem->loadByProduct(1);
         $this->assertEquals(95, $stockItem->getStockQty());
     }
diff --git a/dev/tests/integration/testsuite/Magento/Sales/_files/order_info.php b/dev/tests/integration/testsuite/Magento/Sales/_files/order_info.php
index f964315b3b7..cda5374ec05 100644
--- a/dev/tests/integration/testsuite/Magento/Sales/_files/order_info.php
+++ b/dev/tests/integration/testsuite/Magento/Sales/_files/order_info.php
@@ -41,7 +41,12 @@ $product->setTypeId(
 )->setPrice(
     10
 )->setStockData(
-    array('use_config_manage_stock' => 1, 'qty' => 100, 'is_qty_decimal' => 0, 'is_in_stock' => 100)
+    array(
+        'use_config_manage_stock' => 1,
+        'qty'                     => 100,
+        'is_qty_decimal'          => 0,
+        'is_in_stock'             => 1
+    )
 )->setVisibility(
     \Magento\Catalog\Model\Product\Visibility::VISIBILITY_BOTH
 )->setStatus(
diff --git a/dev/tests/integration/testsuite/Magento/Test/Integrity/Modular/LayoutFilesTest.php b/dev/tests/integration/testsuite/Magento/Test/Integrity/Modular/LayoutFilesTest.php
index 85e671eb071..8ca7fbfd518 100644
--- a/dev/tests/integration/testsuite/Magento/Test/Integrity/Modular/LayoutFilesTest.php
+++ b/dev/tests/integration/testsuite/Magento/Test/Integrity/Modular/LayoutFilesTest.php
@@ -119,6 +119,7 @@ class LayoutFilesTest extends \PHPUnit_Framework_TestCase
                 'value' => 'Magento\CustomerSegment\Model\Resource\Segment\Report\Detail\Collection'
             ),
             array($typeAttr => 'helper', 'helper' => 'Magento\Pbridge\Helper\Data::getReviewButtonTemplate'),
+            array($typeAttr => 'helper', 'helper' => 'Magento\Pbridge\Helper\Data::getContinueButtonTemplate'),
             array($typeAttr => 'options', 'model' => 'Magento\Search\Model\Adminhtml\Search\Grid\Options'),
             array($typeAttr => 'options', 'model' => 'Magento\Logging\Model\Resource\Grid\ActionsGroup'),
             array($typeAttr => 'options', 'model' => 'Magento\Logging\Model\Resource\Grid\Actions')
diff --git a/dev/tests/js/jsTestDriver.php.dist b/dev/tests/js/jsTestDriver.php.dist
index 701571acf86..f7f5c70aa63 100644
--- a/dev/tests/js/jsTestDriver.php.dist
+++ b/dev/tests/js/jsTestDriver.php.dist
@@ -32,7 +32,7 @@ return array(
         '/dev/tests/js/framework',
         '/lib/web/mage/translate.js',
         '/lib/web/mage/webapi.js',
-        '/lib/web/jquery/jquery-ui-timepicker-addon-1.0.1.js',
+        '/lib/web/jquery/jquery-ui-timepicker-addon.js',
         '/lib/web/jquery/jquery.tmpl.min.js',
         '/dev/tests/js/framework',
         '/app/code/Magento/DesignEditor/view/adminhtml/web/js/base.js',
diff --git a/dev/tests/static/testsuite/Magento/Test/Legacy/ObsoleteCodeTest.php b/dev/tests/static/testsuite/Magento/Test/Legacy/ObsoleteCodeTest.php
index 18b8004586c..7cf7a9155ef 100644
--- a/dev/tests/static/testsuite/Magento/Test/Legacy/ObsoleteCodeTest.php
+++ b/dev/tests/static/testsuite/Magento/Test/Legacy/ObsoleteCodeTest.php
@@ -445,7 +445,6 @@ class ObsoleteCodeTest extends \PHPUnit_Framework_TestCase
             list($constant, $class, $replacement) = $row;
             if ($class) {
                 $fullyQualified = "{$class}::{$constant}";
-                $fullyQualified = strtr($fullyQualified, array('\\' => '\\\\'));
                 $regex = preg_quote($fullyQualified);
                 if ($this->_isClassOrInterface($content, $class)) {
                     $regex .= '|' . $this->_getClassConstantDefinitionRegExp($constant)
diff --git a/dev/tests/static/testsuite/Magento/Test/Legacy/_files/obsolete_methods.php b/dev/tests/static/testsuite/Magento/Test/Legacy/_files/obsolete_methods.php
index e3181c66e2a..3784f405985 100644
--- a/dev/tests/static/testsuite/Magento/Test/Legacy/_files/obsolete_methods.php
+++ b/dev/tests/static/testsuite/Magento/Test/Legacy/_files/obsolete_methods.php
@@ -1721,4 +1721,11 @@ return array(
         'Magento\Framework\View\Asset\ModuleNotation\Resolver::convertModuleNotationToPath'
     ],
     ['getViewFile', 'Magento\Framework\View\FileSystem', 'Magento\Framework\View\Asset\File::getSourceFile()'],
+    ['convertOldColumnDefinition', 'Magento\Framework\DB\Helper\AbstractHelper'],
+    ['changeItemStatus', 'Magento\CatalogInventory\Model\Stock\Status'],
+    ['getWebsiteDefaultStoreId', 'Magento\CatalogInventory\Model\Stock\Status'],
+    ['getProductData', 'Magento\CatalogInventory\Model\Stock\Status'],
+    ['getProductData', 'Magento\CatalogInventory\Model\Resource\Stock\Status'],
+    ['getProduct', 'Magento\CatalogInventory\Model\Stock\Item'],
+    ['reset', 'Magento\CatalogInventory\Model\Stock\Item'],
 );
diff --git a/dev/tests/static/testsuite/Magento/Test/Legacy/_files/obsolete_properties.php b/dev/tests/static/testsuite/Magento/Test/Legacy/_files/obsolete_properties.php
index 631212db1a7..202e86a8cb9 100644
--- a/dev/tests/static/testsuite/Magento/Test/Legacy/_files/obsolete_properties.php
+++ b/dev/tests/static/testsuite/Magento/Test/Legacy/_files/obsolete_properties.php
@@ -336,4 +336,6 @@ return array(
     ['_tierPriceDefaultTemplate', 'Magento\Catalog\Block\Product\AbstractProduct'],
     ['_mimeTypes', 'Magento\Framework\File\Transfer\Adapter\Http', '\Magento\Framework\File\Mime::$mimeTypes'],
     ['_viewFileResolution', 'Magento\Framework\View\FileSystem', '_fileResolution, _localeFileResolution'],
+    ['_inventoryModel', 'Magento\AdvancedCheckout\Model\Resource\Sku\Errors\Grid\Collection'],
+    ['_productInstance', 'Magento\CatalogInventory\Model\Stock\Item'],
 );
diff --git a/dev/tests/static/testsuite/Magento/Test/Php/_files/phpcpd/blacklist/common.txt b/dev/tests/static/testsuite/Magento/Test/Php/_files/phpcpd/blacklist/common.txt
index a9236dc5262..ecbbe2237cd 100644
--- a/dev/tests/static/testsuite/Magento/Test/Php/_files/phpcpd/blacklist/common.txt
+++ b/dev/tests/static/testsuite/Magento/Test/Php/_files/phpcpd/blacklist/common.txt
@@ -43,6 +43,7 @@ Magento/Catalog/Model/Resource/Product
 Magento/Catalog/Model/Layer
 Magento/Catalog/Model/Layer/Search.php
 Magento/Catalog/Model/Layer/Category.php
+Magento/Catalog/Service/V1/Data
 Magento/CatalogRule/Block/Adminhtml/Promo/Catalog/Edit/Tab
 Magento/Checkout/Block/Onepage
 Magento/Cms/Block/Adminhtml/Page/Edit
diff --git a/dev/tests/unit/testsuite/Magento/AdminNotification/Block/ToolbarEntryTest.php b/dev/tests/unit/testsuite/Magento/AdminNotification/Block/ToolbarEntryTest.php
index ba0860e5091..4d8d7ecd32d 100644
--- a/dev/tests/unit/testsuite/Magento/AdminNotification/Block/ToolbarEntryTest.php
+++ b/dev/tests/unit/testsuite/Magento/AdminNotification/Block/ToolbarEntryTest.php
@@ -62,4 +62,31 @@ class ToolbarEntryTest extends \PHPUnit_Framework_TestCase
         $block = $this->_getBlockInstance($notificationsCount);
         $this->assertEquals($notificationsCount, $block->getUnreadNotificationCount());
     }
+
+    public function testGetLatestUnreadNotifications()
+    {
+        $helper = new \Magento\TestFramework\Helper\ObjectManager($this);
+
+        // 1. Create mocks
+        $notificationList = $this->getMockBuilder('Magento\AdminNotification\Model\Resource\Inbox\Collection\Unread')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        /** @var \Magento\AdminNotification\Block\ToolbarEntry $model */
+        $model = $helper->getObject('Magento\AdminNotification\Block\ToolbarEntry',
+            ['notificationList' => $notificationList]
+        );
+
+        // 2. Set expectations
+        $notificationList->expects($this->atLeastOnce())
+            ->method('setPageSize')
+            ->with(\Magento\AdminNotification\Block\ToolbarEntry::NOTIFICATIONS_NUMBER)
+            ->will($this->returnSelf());
+
+        // 3. Run tested method
+        $result = $model->getLatestUnreadNotifications();
+
+        // 4. Compare actual result with expected result
+        $this->assertEquals($notificationList, $result);
+    }
 }
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Model/Resource/Product/Link/Product/CollectionTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Model/Resource/Product/Link/Product/CollectionTest.php
new file mode 100644
index 00000000000..05b4c4a99e8
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Model/Resource/Product/Link/Product/CollectionTest.php
@@ -0,0 +1,164 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Model\Resource\Product\Link\Product;
+
+use Magento\TestFramework\Helper\ObjectManager as ObjectManagerHelper;
+
+/**
+ * @SuppressWarnings(PHPMD.CouplingBetweenObjects)
+ * @SuppressWarnings(PHPMD.TooManyFields)
+ */
+class CollectionTest extends \PHPUnit_Framework_TestCase
+{
+    /** @var \Magento\Catalog\Model\Resource\Product\Link\Product\Collection */
+    protected $collection;
+
+    /** @var ObjectManagerHelper */
+    protected $objectManagerHelper;
+
+    /** @var \Magento\Core\Model\EntityFactory|\PHPUnit_Framework_MockObject_MockObject */
+    protected $entityFactoryMock;
+
+    /** @var \Magento\Logger|\PHPUnit_Framework_MockObject_MockObject */
+    protected $loggerMock;
+
+    /** @var \Magento\Data\Collection\Db\FetchStrategyInterface|\PHPUnit_Framework_MockObject_MockObject */
+    protected $fetchStrategyMock;
+
+    /** @var \Magento\Event\ManagerInterface|\PHPUnit_Framework_MockObject_MockObject */
+    protected $managerInterfaceMock;
+
+    /** @var \Magento\Eav\Model\Config|\PHPUnit_Framework_MockObject_MockObject */
+    protected $configMock;
+
+    /** @var \Magento\Framework\App\Resource|\PHPUnit_Framework_MockObject_MockObject */
+    protected $resourceMock;
+
+    /** @var \PHPUnit_Framework_MockObject_MockObject */
+    protected $entityFactoryMock2;
+
+    /** @var \Magento\Catalog\Model\Resource\Helper|\PHPUnit_Framework_MockObject_MockObject */
+    protected $helperMock;
+
+    /** @var \Magento\Validator\UniversalFactory|\PHPUnit_Framework_MockObject_MockObject */
+    protected $universalFactoryMock;
+
+    /** @var \Magento\Store\Model\StoreManagerInterface|\PHPUnit_Framework_MockObject_MockObject */
+    protected $storeManagerMock;
+
+    /** @var \Magento\Catalog\Helper\Data|\PHPUnit_Framework_MockObject_MockObject */
+    protected $catalogHelperMock;
+
+    /** @var \Magento\Catalog\Model\Indexer\Product\Flat\State|\PHPUnit_Framework_MockObject_MockObject */
+    protected $stateMock;
+
+    /** @var \Magento\Framework\App\Config\ScopeConfigInterface|\PHPUnit_Framework_MockObject_MockObject */
+    protected $scopeConfigInterfaceMock;
+
+    /** @var \PHPUnit_Framework_MockObject_MockObject */
+    protected $optionFactoryMock;
+
+    /** @var \Magento\Catalog\Model\Resource\Url|\PHPUnit_Framework_MockObject_MockObject */
+    protected $urlMock;
+
+    /** @var \Magento\Stdlib\DateTime\TimezoneInterface|\PHPUnit_Framework_MockObject_MockObject */
+    protected $timezoneInterfaceMock;
+
+    /** @var \Magento\Customer\Model\Session|\PHPUnit_Framework_MockObject_MockObject */
+    protected $sessionMock;
+
+    /** @var \Magento\Stdlib\DateTime|\PHPUnit_Framework_MockObject_MockObject */
+    protected $dateTimeMock;
+
+    protected function setUp()
+    {
+        $this->entityFactoryMock = $this->getMock('Magento\Core\Model\EntityFactory', [], [], '', false);
+        $this->loggerMock = $this->getMock('Magento\Framework\Logger', [], [], '', false);
+        $this->fetchStrategyMock = $this->getMock('Magento\Framework\Data\Collection\Db\FetchStrategyInterface');
+        $this->managerInterfaceMock = $this->getMock('Magento\Framework\Event\ManagerInterface');
+        $this->configMock = $this->getMock('Magento\Eav\Model\Config', [], [], '', false);
+        $this->resourceMock = $this->getMock('Magento\Framework\App\Resource', [], [], '', false);
+        $this->entityFactoryMock2 = $this->getMock('Magento\Eav\Model\EntityFactory');
+        $this->helperMock = $this->getMock('Magento\Catalog\Model\Resource\Helper', [], [], '', false);
+        $entity = $this->getMock('Magento\Eav\Model\Entity\AbstractEntity', [], [], '', false);
+        $adapter = $this->getMockForAbstractClass('Zend_Db_Adapter_Abstract', [], '', false);
+        $entity->expects($this->any())->method('getReadConnection')->will($this->returnValue($adapter));
+        $entity->expects($this->any())->method('getDefaultAttributes')->will($this->returnValue([]));
+        $this->universalFactoryMock = $this->getMock('Magento\Framework\Validator\UniversalFactory', [], [], '', false);
+        $this->universalFactoryMock->expects($this->any())->method('create')->will($this->returnValue($entity));
+        $this->storeManagerMock = $this->getMockForAbstractClass('Magento\Store\Model\StoreManagerInterface');
+        $this->storeManagerMock
+            ->expects($this->any())
+            ->method('getStore')
+            ->will($this->returnCallback(
+                function ($store) {
+                    return is_object($store) ? $store : new \Magento\Framework\Object(array('id' => 42));
+                }
+            ));
+        $this->catalogHelperMock = $this->getMock('Magento\Catalog\Helper\Data', [], [], '', false);
+        $this->stateMock = $this->getMock('Magento\Catalog\Model\Indexer\Product\Flat\State', [], [], '', false);
+        $this->scopeConfigInterfaceMock = $this->getMock('Magento\Framework\App\Config\ScopeConfigInterface');
+        $this->optionFactoryMock = $this->getMock('Magento\Catalog\Model\Product\OptionFactory');
+        $this->urlMock = $this->getMock('Magento\Catalog\Model\Resource\Url', [], [], '', false);
+        $this->timezoneInterfaceMock = $this->getMock('Magento\Framework\Stdlib\DateTime\TimezoneInterface');
+        $this->sessionMock = $this->getMock('Magento\Customer\Model\Session', [], [], '', false);
+        $this->dateTimeMock = $this->getMock('Magento\Framework\Stdlib\DateTime');
+        $this->objectManagerHelper = new ObjectManagerHelper($this);
+        $this->collection = $this->objectManagerHelper->getObject(
+            'Magento\Catalog\Model\Resource\Product\Link\Product\Collection',
+            [
+                'entityFactory' => $this->entityFactoryMock,
+                'logger' => $this->loggerMock,
+                'fetchStrategy' => $this->fetchStrategyMock,
+                'eventManager' => $this->managerInterfaceMock,
+                'eavConfig' => $this->configMock,
+                'resource' => $this->resourceMock,
+                'eavEntityFactory' => $this->entityFactoryMock2,
+                'resourceHelper' => $this->helperMock,
+                'universalFactory' => $this->universalFactoryMock,
+                'storeManager' => $this->storeManagerMock,
+                'catalogData' => $this->catalogHelperMock,
+                'catalogProductFlatState' => $this->stateMock,
+                'scopeConfig' => $this->scopeConfigInterfaceMock,
+                'productOptionFactory' => $this->optionFactoryMock,
+                'catalogUrl' => $this->urlMock,
+                'localeDate' => $this->timezoneInterfaceMock,
+                'customerSession' => $this->sessionMock,
+                'dateTime' => $this->dateTimeMock
+            ]
+        );
+    }
+
+    public function testSetProduct()
+    {
+        /** @var \Magento\Catalog\Model\Product|\PHPUnit_Framework_MockObject_MockObject $product */
+        $product = $this->getMock('Magento\Catalog\Model\Product', [], [], '', false);
+        $product->expects($this->any())->method('getId')->will($this->returnValue('5'));
+        $productStore = new \Magento\Framework\Object(array('id' => 33));
+        $product->expects($this->any())->method('getStore')->will($this->returnValue($productStore));
+        $this->collection->setProduct($product);
+        $this->assertEquals(33, $this->collection->getStoreId());
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ConverterTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ConverterTest.php
new file mode 100644
index 00000000000..eb59a3744eb
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ConverterTest.php
@@ -0,0 +1,112 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data;
+
+use Magento\Catalog\Service\V1\Data\ProductBuilder;
+use Magento\Catalog\Service\V1\Data\Product as ProductDataObject;
+
+class ConverterTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @var ProductBuilder
+     */
+    protected $productBuilder;
+
+    /**
+     * @var Converter | \PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $converter;
+
+    protected function setUp()
+    {
+        $this->productBuilder = $this->getMock(
+            'Magento\Catalog\Service\V1\Data\ProductBuilder',
+            [],
+            [],
+            '',
+            false
+        );
+    }
+
+    public function testCreateProductDataFromModel()
+    {
+        $productModelMock = $this->getMockBuilder('\Magento\Catalog\Model\Product')
+            ->disableOriginalConstructor()
+            ->getMock();
+        $attrCodes = ['sku', 'price', 'status', 'updatedAt', 'entity_id'];
+        $this->productBuilder->expects($this->once())
+            ->method('getCustomAttributesCodes')
+            ->will($this->returnValue($attrCodes));
+
+        $attributes = [
+            ProductDataObject::SKU => ProductDataObject::SKU . 'value',
+            ProductDataObject::PRICE => ProductDataObject::PRICE . 'value',
+            ProductDataObject::STATUS => ProductDataObject::STATUS . 'dataValue',
+            ProductDataObject::ID => 'entity_id' . 'value'
+        ];
+        $this->productBuilder->expects($this->once())
+            ->method('populateWithArray')
+            ->with($attributes);
+
+        $this->productBuilder->expects($this->once())
+            ->method('getData')
+            ->will($this->returnValue($attributes));
+
+        $this->productBuilder->expects($this->once())
+            ->method('create')
+            ->will($this->returnValue(new ProductDataObject($this->productBuilder)));
+
+        $dataUsingMethodCallback = $this->returnCallback(
+            function ($attrCode) {
+                if (in_array($attrCode, ['sku', 'price', 'entity_id'])) {
+                    return $attrCode . 'value';
+                }
+                return null;
+            }
+        );
+        $productModelMock->expects($this->exactly(count($attrCodes)))
+            ->method('getDataUsingMethod')
+            ->will($dataUsingMethodCallback);
+
+        $dataCallback = $this->returnCallback(
+            function ($attrCode) {
+                if ($attrCode == 'status') {
+                    return $attrCode . 'dataValue';
+                }
+                return null;
+            }
+        );
+        $productModelMock->expects($this->exactly(2))
+            ->method('getData')
+            ->will($dataCallback);
+
+        $this->converter = new Converter($this->productBuilder);
+        $productData = $this->converter->createProductDataFromModel($productModelMock);
+        $this->assertEquals(ProductDataObject::SKU . 'value', $productData->getSku());
+        $this->assertEquals('entity_id' . 'value', $productData->getId());
+        $this->assertEquals(ProductDataObject::PRICE . 'value', $productData->getPrice());
+        $this->assertEquals(ProductDataObject::STATUS . 'dataValue', $productData->getStatus());
+        $this->assertEquals(null, $productData->getUpdatedAt());
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataBuilderTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataBuilderTest.php
new file mode 100644
index 00000000000..dc3da1419e7
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataBuilderTest.php
@@ -0,0 +1,154 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data\Eav;
+
+use Magento\Catalog\Service\V1\Data\Eav\AttributeMetadata;
+
+class AttributeMetadataBuilderTest extends \PHPUnit_Framework_TestCase
+{
+    /** @var \Magento\Catalog\Service\V1\Data\Eav\AttributeMetadataBuilder|\PHPUnit_Framework_TestCase */
+    protected $attributeMetadataBuilder;
+
+    /** @var \Magento\Catalog\Service\V1\Data\Eav\OptionBuilder */
+    private $optionBuilderMock;
+
+    /** @var \Magento\Catalog\Service\V1\Data\Eav\ValidationRuleBuilder */
+    private $validationRuleBuilderMock;
+
+    /** @var \Magento\Catalog\Service\V1\Data\Eav\ValidationRule[] */
+    protected $validationRules;
+
+    /** @var \Magento\Catalog\Service\V1\Data\Eav\Option[] */
+    protected $optionRules;
+
+    protected function setUp()
+    {
+        $objectManager = new \Magento\TestFramework\Helper\ObjectManager($this);
+        
+        $this->optionBuilderMock =
+            $this->getMock('Magento\Catalog\Service\V1\Data\Eav\OptionBuilder', [], [], '', false);
+
+        $this->validationRuleBuilderMock =
+            $this->getMock('Magento\Catalog\Service\V1\Data\Eav\ValidationRuleBuilder', [], [], '', false);
+
+        $this->validationRules = array(
+            [0 => $this->getMock('Magento\Catalog\Service\V1\Data\Eav\ValidationRule', [], [], '', false)],
+            [1 => $this->getMock('Magento\Catalog\Service\V1\Data\Eav\ValidationRule', [], [], '', false)]
+        );
+
+        $this->optionRules = array(
+            [0 => $this->getMock('Magento\Catalog\Service\V1\Data\Eav\Option', [], [], '', false)],
+            [1 => $this->getMock('Magento\Catalog\Service\V1\Data\Eav\Option', [], [], '', false)]
+        );
+
+        $this->attributeMetadataBuilder = $objectManager->getObject(
+            'Magento\Catalog\Service\V1\Data\Eav\AttributeMetadataBuilder',
+            [
+                'optionBuilder' => $this->optionBuilderMock,
+                'validationRuleBuilder' => $this->validationRuleBuilderMock
+            ]
+        );
+    }
+
+    /**
+     * @dataProvider setValueDataProvider
+     */
+    public function testSetValue($method, $value, $getMethod)
+    {
+        $data = $this->attributeMetadataBuilder->$method($value)->create();
+        $this->assertEquals($value, $data->$getMethod());
+    }
+
+    public function setValueDataProvider()
+    {
+        return array(
+            ['setAttributeCode', 'code', 'getAttributeCode'],
+            ['setFrontendInput', '<br>', 'getFrontendInput'],
+            ['setValidationRules', $this->validationRules, 'getValidationRules'],
+            ['setVisible', true, 'isVisible'],
+            ['setRequired', true, 'isRequired'],
+            ['setOptions', $this->optionRules, 'getOptions'],
+            ['setUserDefined', false, 'isUserDefined'],
+            ['setFrontendLabel', 'Label', 'getFrontendLabel'],
+            ['setFrontendClass', 'Class', 'getFrontendClass'],
+            ['setNote', 'Text Note', 'getNote'],
+        );
+    }
+
+    public function testPopulateWithArray()
+    {
+        $this->optionBuilderMock
+            ->expects($this->at(0))
+            ->method('populateWithArray')
+            ->with($this->optionRules[0])
+            ->will($this->returnSelf());
+        $this->optionBuilderMock
+            ->expects($this->at(1))
+            ->method('create')
+            ->will($this->returnValue($this->optionRules[0]));
+        $this->optionBuilderMock
+            ->expects($this->at(2))
+            ->method('populateWithArray')
+            ->with($this->optionRules[1])
+            ->will($this->returnSelf());
+        $this->optionBuilderMock
+            ->expects($this->at(3))
+            ->method('create')
+            ->will($this->returnValue($this->optionRules[1]));
+
+        $this->validationRuleBuilderMock
+            ->expects($this->at(0))
+            ->method('populateWithArray')
+            ->with($this->validationRules[0])
+            ->will($this->returnSelf());
+        $this->validationRuleBuilderMock
+            ->expects($this->at(1))
+            ->method('create')
+            ->will($this->returnValue($this->validationRules[0]));
+        $this->validationRuleBuilderMock
+            ->expects($this->at(2))
+            ->method('populateWithArray')
+            ->with($this->validationRules[1])
+            ->will($this->returnSelf());
+        $this->validationRuleBuilderMock
+            ->expects($this->at(3))
+            ->method('create')
+            ->will($this->returnValue($this->validationRules[1]));
+
+        $data = array(
+            AttributeMetadata::OPTIONS => $this->optionRules,
+            AttributeMetadata::VALIDATION_RULES => $this->validationRules,
+            'note' => $textNote = 'Text Note',
+            'visible' => $visible = true,
+            'some_key' => 'some_value',
+        );
+
+        $attributeData = $this->attributeMetadataBuilder->populateWithArray($data)->create();
+        $this->assertEquals($textNote, $attributeData->getNote());
+        $this->assertEquals($visible, $attributeData->isVisible());
+        $this->assertEquals($data[AttributeMetadata::OPTIONS], $attributeData->getOptions());
+        $this->assertEquals($data[AttributeMetadata::VALIDATION_RULES], $attributeData->getValidationRules());
+        $this->assertArrayNotHasKey('some_key', $attributeData->__toArray());
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataTest.php
new file mode 100644
index 00000000000..5702ed54636
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/AttributeMetadataTest.php
@@ -0,0 +1,131 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data\Eav;
+
+class AttributeMetadataTest extends \PHPUnit_Framework_TestCase
+{
+    /** @var \Magento\Framework\Service\Data\AbstractObjectBuilder|\PHPUnit_Framework_TestCase */
+    protected $builderMock;
+
+    /** @var \Magento\Catalog\Service\V1\Data\Eav\ValidationRule[] */
+    protected $validationRules;
+
+    /** @var \Magento\Catalog\Service\V1\Data\Eav\Option[] */
+    protected $optionRules;
+
+    protected function setUp()
+    {
+        $this->builderMock = $this->getMockBuilder('Magento\Framework\Service\Data\AbstractObjectBuilder')
+            ->setMethods(array('getData'))
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $this->validationRules = array(
+            $this->getMock('Magento\Catalog\Service\V1\Data\Eav\ValidationRule', [], [], '', false),
+            $this->getMock('Magento\Catalog\Service\V1\Data\Eav\ValidationRule', [], [], '', false)
+        );
+
+        $this->optionRules = array(
+            $this->getMock('Magento\Catalog\Service\V1\Data\Eav\Option', [], [], '', false),
+            $this->getMock('Magento\Catalog\Service\V1\Data\Eav\Option', [], [], '', false)
+        );
+    }
+
+    /**
+     * Test constructor and getters
+     *
+     * @dataProvider constructorAndGettersDataProvider
+     */
+    public function testConstructorAndGetters($method, $key, $expectedValue)
+    {
+        $this->builderMock
+            ->expects($this->once())
+            ->method('getData')
+            ->will($this->returnValue([$key => $expectedValue]));
+        $attributeMetadata = new AttributeMetadata($this->builderMock);
+        $this->assertEquals($expectedValue, $attributeMetadata->$method());
+    }
+
+    public function constructorAndGettersDataProvider()
+    {
+        return array(
+            ['getAttributeCode', AttributeMetadata::ATTRIBUTE_CODE, 'code'],
+            ['getFrontendInput', AttributeMetadata::FRONTEND_INPUT, '<br>'],
+            ['getValidationRules', AttributeMetadata::VALIDATION_RULES, $this->validationRules],
+            ['isVisible', AttributeMetadata::VISIBLE, true],
+            ['isRequired', AttributeMetadata::REQUIRED, true],
+            ['getOptions', AttributeMetadata::OPTIONS, $this->optionRules],
+            ['isUserDefined', AttributeMetadata::USER_DEFINED, false],
+            ['getFrontendLabel', AttributeMetadata::FRONTEND_LABEL, 'Label'],
+            ['getNote', AttributeMetadata::NOTE, 'Text Note'],
+            ['getBackendType', AttributeMetadata::BACKEND_TYPE, 'Type']
+        );
+    }
+
+    /**
+     * Test applyTy method of builder
+     *
+     * ApplyTo method transform string to array
+     *
+     * @dataProvider applyToDataProvider()
+     *
+     * @param $applyTo
+     */
+    public function testApplyTo($applyTo)
+    {
+        $objectManager = new \Magento\TestFramework\Helper\ObjectManager($this);
+        /** @var \Magento\Catalog\Service\V1\Data\Eav\OptionBuilder $optionBuilder */
+        $optionBuilder = $objectManager->getObject('Magento\Catalog\Service\V1\Data\Eav\OptionBuilder');
+        /** @var \Magento\Catalog\Service\V1\Data\Eav\ValidationRuleBuilder $validationRuleBuilder */
+        $validationRuleBuilder = $objectManager->getObject(
+            'Magento\Catalog\Service\V1\Data\Eav\ValidationRuleBuilder'
+        );
+
+        $attributeBuilder = $objectManager->getObject(
+            'Magento\Catalog\Service\V1\Data\Eav\AttributeMetadataBuilder',
+            [
+                'optionBuilder' => $optionBuilder,
+                'validationRuleBuilder' => $validationRuleBuilder
+            ]
+        );
+        $attributeBuilder->populateWithArray([AttributeMetadata::APPLY_TO => $applyTo]);
+
+        $attributeMetadata = new AttributeMetadata($attributeBuilder);
+        $this->assertTrue(is_array($attributeMetadata->getApplyTo()));
+        $this->assertEquals(3, count($attributeMetadata->getApplyTo()));
+
+        $attributeBuilder->setApplyTo($applyTo);
+        $attributeMetadata = new AttributeMetadata($attributeBuilder);
+        $this->assertTrue(is_array($attributeMetadata->getApplyTo()));
+        $this->assertEquals(3, count($attributeMetadata->getApplyTo()));
+    }
+
+    public function applyToDataProvider()
+    {
+        return array(array(
+            'simple,virtual,bundle',
+            array('simple', 'virtual', 'bundle')
+        ));
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/OptionTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/OptionTest.php
new file mode 100644
index 00000000000..9b41006f367
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/Eav/OptionTest.php
@@ -0,0 +1,44 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data\Eav;
+
+use Magento\Catalog\Service\V1\Data\Eav\Option;
+use Magento\Catalog\Service\V1\Data\Eav\OptionBuilder;
+
+class OptionTest extends \PHPUnit_Framework_TestCase
+{
+    const LABEL = 'LABEL';
+
+    const VALUE = 'VALUE';
+
+    public function testConstructorAndGetters()
+    {
+        $helper = new \Magento\TestFramework\Helper\ObjectManager($this);
+        $optionBuilder = $helper->getObject('\Magento\Catalog\Service\V1\Data\Eav\OptionBuilder');
+        $optionBuilder->setLabel(self::LABEL)->setValue(self::VALUE);
+        $option = new Option($optionBuilder);
+        $this->assertSame(self::LABEL, $option->getLabel());
+        $this->assertSame(self::VALUE, $option->getValue());
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ProductBuilderTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ProductBuilderTest.php
new file mode 100644
index 00000000000..36569596be8
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ProductBuilderTest.php
@@ -0,0 +1,126 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data;
+
+class ProductBuilderTest extends \PHPUnit_Framework_TestCase
+{
+    /** @var \Magento\Catalog\Service\V1\Data\ProductBuilder|\PHPUnit_Framework_TestCase */
+    protected $_productBuilder;
+
+    /** @var \Magento\TestFramework\Helper\ObjectManager */
+    protected $_objectManager;
+
+    /** @var \Magento\Catalog\Service\V1\ProductMetadataService */
+    private $_productMetadataService;
+
+    /** @var \Magento\Framework\Service\Data\Eav\AttributeValueBuilder */
+    private $_valueBuilder;
+
+    protected function setUp()
+    {
+        $this->_objectManager = new \Magento\TestFramework\Helper\ObjectManager($this);
+        
+        $this->_productMetadataService = $this->getMockBuilder(
+            'Magento\Catalog\Service\V1\ProductMetadataService'
+        )->setMethods(
+            array('getCustomAttributesMetadata')
+        )->disableOriginalConstructor()->getMock();
+        $this->_productMetadataService
+            ->expects($this->any())
+            ->method('getCustomAttributesMetadata')
+            ->will($this->returnValue(
+                array(
+                    new \Magento\Framework\Object(array('attribute_code' => 'attribute_code_1')),
+                    new \Magento\Framework\Object(array('attribute_code' => 'attribute_code_2'))
+                )
+            )
+        );
+        $this->_valueBuilder = $this->_objectManager->getObject(
+            'Magento\Framework\Service\Data\Eav\AttributeValueBuilder'
+        );
+        $this->_productBuilder = $this->_objectManager->getObject(
+            'Magento\Catalog\Service\V1\Data\ProductBuilder',
+            [
+                'valueBuilder' => $this->_valueBuilder,
+                'metadataService' => $this->_productMetadataService
+            ]
+        );
+    }
+
+    /**
+     * @param $method
+     * @param $value
+     * @param $getMethod
+     *
+     * @dataProvider setValueDataProvider
+     */
+    public function testSetValue($method, $value, $getMethod)
+    {
+        $productData = $this->_productBuilder->$method($value)->create();
+        $this->assertEquals($value, $productData->$getMethod());
+    }
+
+    /**
+     * @return array
+     */
+    public function setValueDataProvider()
+    {
+        return [
+            ['setId', 100, 'getId'],
+            ['setSku', 'product_sku', 'getSku'],
+            ['setName', 'buhanka hleba', 'getName'],
+            ['setStoreId', 0, 'getStoreId'],
+            ['setPrice', 100.00, 'getPrice'],
+            ['setVisibility', 1, 'getVisibility'],
+            ['setTypeId', 2, 'getTypeId'],
+            ['setStatus', 2, 'getStatus'],
+            ['setWeight', 72.5, 'getWeight']
+        ];
+    }
+
+    /**
+     * @return array
+     */
+    public function readonlyFieldProvider()
+    {
+        return [
+            ['setCreatedAt', '2014-05-23', 'getCreatedAt'],
+            ['setUpdatedAt', '2014-05-25', 'getUpdatedAt'],
+        ];
+    }
+    /**
+     * @dataProvider readonlyFieldProvider
+     * @expectedException \Magento\Framework\Exception\InputException
+     */
+    public function testReadonlyFields($method)
+    {
+        $this->_productBuilder->$method('');
+    }
+
+    public function testGetCustomAttributes()
+    {
+        $expectedAttributesCodes = ['attribute_code_1', 'attribute_code_2'];
+        $this->assertEquals($expectedAttributesCodes, $this->_productBuilder->getCustomAttributesCodes());
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ProductMapperTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ProductMapperTest.php
new file mode 100644
index 00000000000..f35c932d4f2
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Data/ProductMapperTest.php
@@ -0,0 +1,71 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1\Data;
+
+use Magento\TestFramework\Helper\ObjectManager as ObjectManagerHelper;
+
+class ProductMapperTest extends \PHPUnit_Framework_TestCase
+{
+    /** @var ProductMapper */
+    protected $object;
+
+    /** @var ObjectManagerHelper */
+    protected $objectManagerHelper;
+
+    protected function setUp()
+    {
+        $this->objectManagerHelper = new ObjectManagerHelper($this);
+    }
+
+    public function testToModel()
+    {
+        $productFactory = $this->getMockBuilder('Magento\Catalog\Model\ProductFactory')
+            ->setMethods(['create'])
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        /** @var \Magento\Catalog\Service\V1\Data\ProductMapper $productMapper */
+        $productMapper = $this->objectManagerHelper->getObject(
+            'Magento\Catalog\Service\V1\Data\ProductMapper',
+            ['productFactory' => $productFactory]
+        );
+
+        $product = $this->getMockBuilder('Magento\Catalog\Service\V1\Data\Product')
+               ->disableOriginalConstructor()
+               ->getMock();
+        $product->expects($this->once())->method('__toArray')->will($this->returnValue([
+            'test_code' => 'test_value',
+        ]));
+
+        /** @var \Magento\Catalog\Model\Product|\PHPUnit_Framework_MockObject_MockObject $productModel */
+        $productModel = $this->getMockBuilder('Magento\Catalog\Model\Product')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $productFactory->expects($this->once())->method('create')->will($this->returnValue($productModel));
+
+        $this->assertEquals($productModel, $productMapper->toModel($product));
+
+    }
+}
\ No newline at end of file
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/ReadServiceTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/ReadServiceTest.php
index 82e91616653..a0c7d31b01d 100644
--- a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/ReadServiceTest.php
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/ReadServiceTest.php
@@ -95,7 +95,7 @@ class ReadServiceTest extends \PHPUnit_Framework_TestCase
         );
 
         $this->productLoaderMock = $this->getMock(
-            'Magento\Catalog\Service\V1\Product\Link\ProductLoader',
+            'Magento\Catalog\Service\V1\Product\ProductLoader',
             [],
             [],
             '',
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/WriteServiceTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/WriteServiceTest.php
index 2d5d764f104..bb55450a0da 100644
--- a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/WriteServiceTest.php
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/WriteServiceTest.php
@@ -79,7 +79,7 @@ class WriteServiceTest extends \PHPUnit_Framework_TestCase
         );
 
         $this->productLoaderMock = $this->getMock(
-           'Magento\Catalog\Service\V1\Product\Link\ProductLoader',
+           'Magento\Catalog\Service\V1\Product\ProductLoader',
             [],
             [],
             '',
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/ProductLoaderTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/ProductLoaderTest.php
similarity index 98%
rename from dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/ProductLoaderTest.php
rename to dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/ProductLoaderTest.php
index 347e76b35ba..1f8180d928e 100644
--- a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/Link/ProductLoaderTest.php
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/Product/ProductLoaderTest.php
@@ -22,7 +22,7 @@
  * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
  */
 
-namespace Magento\Catalog\Service\V1\Product\Link;
+namespace Magento\Catalog\Service\V1\Product;
 
 class ProductLoaderTest extends \PHPUnit_Framework_TestCase
 {
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductAttributeReadServiceTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductAttributeReadServiceTest.php
new file mode 100644
index 00000000000..544eb36d345
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductAttributeReadServiceTest.php
@@ -0,0 +1,90 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1;
+
+use Magento\Catalog\Service\V1\Data\ProductAttributeTypeBuilder;
+use Magento\Catalog\Service\V1\ProductMetadataServiceInterface;
+
+class ProductAttributeReadServiceTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * Test for retrieving product attributes types
+     */
+    public function testTypes()
+    {
+        $objectManager = new \Magento\TestFramework\Helper\ObjectManager($this);
+        $inputtypeFactoryMock = $this->getMock(
+            'Magento\Catalog\Model\Product\Attribute\Source\InputtypeFactory',
+            array('create')
+        );
+        $inputtypeFactoryMock->expects($this->once())
+            ->method('create')
+            ->will($this->returnValue(
+                $objectManager->getObject('Magento\Catalog\Model\Product\Attribute\Source\Inputtype')
+            ));
+
+        $helper = new \Magento\TestFramework\Helper\ObjectManager($this);
+        $attributeTypeBuilder = $helper->getObject('\Magento\Catalog\Service\V1\Data\ProductAttributeTypeBuilder');
+        $productAttributeReadService = new ProductAttributeReadService(
+            $objectManager->getObject('Magento\Catalog\Service\V1\ProductMetadataService'),
+            $inputtypeFactoryMock,
+            $attributeTypeBuilder
+        );
+        $types = $productAttributeReadService->types();
+        $this->assertTrue(is_array($types));
+        $this->assertNotEmpty($types);
+        $this->assertInstanceOf('Magento\Catalog\Service\V1\Data\ProductAttributeType', current($types));
+    }
+
+    /**
+     * Test for retrieving product attribute
+     */
+    public function testInfo()
+    {
+        $objectManager = new \Magento\TestFramework\Helper\ObjectManager($this);
+
+        $attributeCode = 'attr_code';
+        $metadataServiceMock = $this->getMock(
+            'Magento\Catalog\Service\V1\ProductMetadataService', array('getAttributeMetadata'),
+            array(),
+            '',
+            false
+        );
+        $metadataServiceMock->expects($this->once())
+            ->method('getAttributeMetadata')
+            ->with(
+                ProductMetadataServiceInterface::ENTITY_TYPE_PRODUCT,
+                $attributeCode
+            );
+
+        /** @var \Magento\Catalog\Service\V1\ProductAttributeReadServiceInterface $service */
+        $service = $objectManager->getObject(
+            'Magento\Catalog\Service\V1\ProductAttributeReadService',
+            array(
+               'metadataService' => $metadataServiceMock
+            )
+        );
+        $service->info($attributeCode);
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductMetadataServiceTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductMetadataServiceTest.php
new file mode 100644
index 00000000000..75b62b0db3c
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductMetadataServiceTest.php
@@ -0,0 +1,89 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Catalog\Service\V1;
+
+use Magento\Catalog\Service\V1\Data\Eav\AttributeMetadataBuilder;
+use Magento\Catalog\Service\V1\Data\Eav\OptionBuilder;
+use Magento\Catalog\Service\V1\Data\Eav\ValidationRuleBuilder;
+
+class ProductMetadataServiceTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * Test getAttributeMetadata
+     */
+    public function testGetAttributeMetadata()
+    {
+        $objectManager = new \Magento\TestFramework\Helper\ObjectManager($this);
+
+        $data = array(
+            'attribute_id' => 1,
+            'attribute_code' => 'description',
+            'frontend_label' => 'English',
+            'store_labels' => array(1 => 'France'),
+            'frontend_input' => 'textarea',
+        );
+
+        //attributeMock
+        $attributeMock = $this->getMock(
+            'Magento\Framework\Object',
+            array('usesSource', 'getSource', 'isScopeGlobal'),
+            array('data' => $data)
+        );
+        $attributeMock->expects($this->any())->method('isScopeGlobal')->will($this->returnValue(true));
+        $attributeMock->expects($this->any())->method('usesSource')->will($this->returnValue(true));
+        $attributeMock->expects($this->any())->method('getSource')
+            ->will($this->returnValue(new \Magento\Framework\Object()));
+
+        // eavConfigMock
+        $eavConfigMock = $this->getMock('Magento\Eav\Model\Config', array('getAttribute'), array(), '', false);
+        $eavConfigMock->expects($this->any())->method('getAttribute')->will($this->returnValue($attributeMock));
+
+        $helper = new \Magento\TestFramework\Helper\ObjectManager($this);
+        $validationRuleBuilder = $helper->getObject('\Magento\Catalog\Service\V1\Data\Eav\ValidationRuleBuilder');
+        $optionBuilder = $helper->getObject('\Magento\Catalog\Service\V1\Data\Eav\OptionBuilder');
+        $attrMetadataBuilder = $objectManager->getObject(
+            'Magento\Catalog\Service\V1\Data\Eav\AttributeMetadataBuilder',
+            [
+                'optionBuilder' => $optionBuilder,
+                'validationRuleBuilder' => $validationRuleBuilder
+            ]
+        );
+
+        // create service
+        $service = $objectManager->getObject('Magento\Catalog\Service\V1\ProductMetadataService',
+            array(
+                'eavConfig' => $eavConfigMock,
+                'attributeMetadataBuilder'
+                    => $attrMetadataBuilder
+            )
+        );
+
+        $dto = $service->getAttributeMetadata('entity_type', 'attr_code');
+        $this->assertInstanceOf('Magento\Framework\Service\Data\AbstractObject', $dto);
+        $this->assertEquals($attributeMock->getFrontendInput(), $dto->getFrontendInput());
+
+        $this->assertTrue(is_array($dto->getFrontendLabel()));
+        $this->assertArrayHasKey('store_id', $dto->getFrontendLabel()[0]);
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductServiceTest.php b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductServiceTest.php
new file mode 100644
index 00000000000..339429f84b4
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Catalog/Service/V1/ProductServiceTest.php
@@ -0,0 +1,403 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Catalog\Service\V1;
+
+use Magento\Framework\Service\V1\Data\SearchCriteriaBuilder;
+use Magento\Framework\Service\V1\Data\FilterBuilder;
+
+/**
+ * Test for \Magento\Catalog\Service\V1\ProductService
+ */
+class ProductServiceTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @var \PHPUnit_Framework_MockObject_MockObject | \Magento\catalog\Service\V1\Product\ProductLoader
+     */
+    protected $_productLoaderMock;
+
+    /**
+     * @var \PHPUnit_Framework_MockObject_MockObject | \Magento\Catalog\Model\Product
+     */
+    protected $_productMock;
+
+    /**
+     * @var \PHPUnit_Framework_MockObject_MockObject | \Magento\Catalog\Model\Resource\Product\CollectionFactory
+     */
+    protected $productCollection;
+
+    /**
+     * @var \Magento\TestFramework\Helper\ObjectManager
+     */
+    protected $_objectManager;
+
+    /**
+     * @var \PHPUnit_Framework_MockObject_MockObject | \Magento\Catalog\Service\V1\Data\SearchResultsBuilder
+     */
+    protected $searchResultsBuilderMock;
+
+    /**
+     * @var \PHPUnit_Framework_MockObject_MockObject | \Magento\Catalog\Service\V1\ProductMetadataServiceInterface
+     */
+    protected $metadataServiceMock;
+
+    /**
+     * @var \PHPUnit_Framework_MockObject_MockObject | \Magento\Catalog\Model\Converter
+     */
+    protected $converterMock;
+
+    /**
+     * @var SearchCriteriaBuilder
+     */
+    protected $_searchBuilder;
+
+    public function setUp()
+    {
+        $this->_objectManager = new \Magento\TestFramework\Helper\ObjectManager($this);
+
+        $this->_productMock = $this->getMockBuilder('Magento\Catalog\Model\Product')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $productFactoryMock = $this->getMockBuilder('Magento\Catalog\Model\ProductFactory')
+            ->disableOriginalConstructor()
+            ->setMethods(['create'])
+            ->getMock();
+        $productFactoryMock
+            ->expects($this->any())
+            ->method('create')
+            ->will($this->returnValue($this->_productMock));
+
+        $this->_productLoaderMock = $this->_objectManager
+            ->getObject(
+                'Magento\Catalog\Service\V1\Product\ProductLoader',
+                ['productFactory' => $productFactoryMock]
+            );
+
+        $this->productCollection = $this->getMockBuilder('Magento\Catalog\Model\Resource\Product\CollectionFactory')
+            ->disableOriginalConstructor()
+            ->setMethods(['create'])
+            ->getMock();
+
+        $this->searchResultsBuilderMock = $this->getMockBuilder('Magento\Catalog\Service\V1\Data\SearchResultsBuilder')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $this->metadataServiceMock = $this->getMockBuilder(
+            '\Magento\Catalog\Service\V1\ProductMetadataServiceInterface'
+        )->disableOriginalConstructor()
+            ->getMock();
+
+        $this->converterMock = $this->getMockBuilder('\Magento\Catalog\Service\V1\Data\Converter')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $filterGroupBuilder = $this->_objectManager
+            ->getObject('Magento\Framework\Service\V1\Data\Search\FilterGroupBuilder');
+        /** @var SearchCriteriaBuilder $searchBuilder */
+        $this->_searchBuilder = $this->_objectManager->getObject(
+            'Magento\Framework\Service\V1\Data\SearchCriteriaBuilder',
+            ['filterGroupBuilder' => $filterGroupBuilder]
+        );
+    }
+
+    public function testDelete()
+    {
+        $productId = 100;
+        $productSku = 'sku-001';
+
+        $this->_productMock->expects($this->at(0))->method('getIdBySku')->will($this->returnValue($productId));
+        $this->_productMock->expects($this->at(1))->method('load')->with($productId);
+        $productService = $this->_createService();
+
+        $this->assertTrue($productService->delete($productSku));
+    }
+
+    public function testDeleteNoSuchEntityException()
+    {
+        $productId = 0;
+        $productSku = 'sku-001';
+
+        $this->_productMock->expects($this->once())->method('getIdBySku')->will($this->returnValue($productId));
+        $productService = $this->_createService();
+
+        $this->setExpectedException(
+            'Magento\Framework\Exception\NoSuchEntityException',
+            "There is no product with provided SKU"
+        );
+
+        $productService->delete($productSku);
+    }
+
+    /**
+     * @return ProductService
+     */
+    private function _createService()
+    {
+        $productService = $this->_objectManager->getObject(
+            'Magento\Catalog\Service\V1\ProductService',
+            [
+                'productLoader' => $this->_productLoaderMock
+            ]
+        );
+        return $productService;
+    }
+
+    public function testSearch()
+    {
+        $metadata = array();
+        $attributeCodes = ['price', 'id', 'sku'];
+        foreach ($attributeCodes as $code) {
+            $attributeMetadataMock = $this->getMockBuilder('\Magento\Catalog\Service\V1\Data\Eav\AttributeMetadata')
+                ->disableOriginalConstructor()
+                ->getMock();
+            $attributeMetadataMock->expects($this->once())
+                ->method('getAttributeCode')
+                ->will($this->returnValue($code));
+            $metadata[] = $attributeMetadataMock;
+        }
+        $this->metadataServiceMock->expects($this->any())
+            ->method('getProductAttributesMetadata')
+            ->will($this->returnValue($metadata));
+
+        $collection = $this->getMockBuilder('\Magento\Catalog\Model\Resource\Product\Collection')
+            ->disableOriginalConstructor()
+            ->getMock();
+        $collection->expects($this->any())->method('addAttributeToSelect');
+        $collection->expects($this->any())->method('joinAttribute');
+        $collection->expects($this->any())->method('addOrder')->with(
+            $this->equalTo('price'),
+            $this->equalTo('ASC')
+        );
+        $collection->expects($this->once())->method('setCurPage')->with($this->equalTo(1));
+        $collection->expects($this->once())->method('setPageSize')->with($this->equalTo(10));
+        $collection->expects($this->once())->method('getSize')->will($this->returnValue(5));
+        $this->productCollection->expects($this->once())
+            ->method('create')
+            ->will($this->returnValue($collection));
+
+        $this->_mockReturnValue(
+            $collection,
+            array(
+                'getSize' => 1,
+                '_getItems' => array($this->_productMock),
+                'getIterator' => new \ArrayIterator(array($this->_productMock))
+            )
+        );
+
+        $productDataBuilder = $this->getMockBuilder('\Magento\Catalog\Service\V1\Data\ProductBuilder')
+            ->disableOriginalConstructor()
+            ->getMock();
+        $productDataBuilder->setId(1);
+        $productDataBuilder->setPrice('10.000');
+        $productDataBuilder->setSku('test');
+        $productDataBuilder->setStoreId(10);
+        $this->converterMock->expects($this->once())
+            ->method('createProductDataFromModel')
+            ->will($this->returnValue($productDataBuilder->create()));
+
+        $this->searchResultsBuilderMock->expects($this->once())
+            ->method('setItems')
+            ->with($this->equalTo(array($productDataBuilder->create())));
+        $this->searchResultsBuilderMock->expects($this->once())
+            ->method('create')
+            ->will($this->returnValue(array($productDataBuilder->create())));
+
+        $productService = $this->_objectManager->getObject(
+            'Magento\Catalog\Service\V1\ProductService',
+            [
+                'productLoader' => $this->_productLoaderMock,
+                'productCollection' => $this->productCollection,
+                'searchResultsBuilder' => $this->searchResultsBuilderMock,
+                'metadataService' => $this->metadataServiceMock,
+                'converter' => $this->converterMock,
+            ]
+        );
+
+        $helper = new \Magento\TestFramework\Helper\ObjectManager($this);
+        $filterBuilder = $helper->getObject('\Magento\Framework\Service\V1\Data\FilterBuilder');
+        $filter = $filterBuilder->setField('price')->setValue('10.000')->setConditionType('eq')->create();
+        $this->_searchBuilder->addFilter([$filter]);
+        $this->_searchBuilder->addSortOrder('price', \Magento\Framework\Service\V1\Data\SearchCriteria::SORT_ASC);
+        $this->_searchBuilder->setCurrentPage(1);
+        $this->_searchBuilder->setPageSize(10);
+        $productService->search($this->_searchBuilder->create());
+    }
+
+    /**
+     * @param \PHPUnit_Framework_MockObject_MockObject $mock
+     * @param array $valueMap
+     */
+    private function _mockReturnValue($mock, $valueMap)
+    {
+        foreach ($valueMap as $method => $value) {
+            $mock->expects($this->any())->method($method)->will($this->returnValue($value));
+        }
+    }
+
+    public function testGet()
+    {
+        $productId = 100;
+        $productSku = 'sku-001';
+
+        $this->_productMock->expects($this->at(0))->method('getIdBySku')->will($this->returnValue($productId));
+        $this->_productMock->expects($this->at(1))->method('load')->with($productId);
+        $this->converterMock->expects($this->once())->method('createProductDataFromModel')->with($this->_productMock);
+
+        $productService = $this->_objectManager->getObject(
+            'Magento\Catalog\Service\V1\ProductService',
+            [
+                'productLoader' => $this->_productLoaderMock,
+                'converter' => $this->converterMock,
+            ]
+        );
+        $productService->get($productSku);
+    }
+
+    public function testGetNoSuchEntityException()
+    {
+        $productId = 0;
+        $productSku = 'sku-001';
+
+        $this->_productMock->expects($this->once())->method('getIdBySku')->will($this->returnValue($productId));
+        $productService = $this->_createService();
+
+        $this->setExpectedException(
+            'Magento\Framework\Exception\NoSuchEntityException',
+            "There is no product with provided SKU"
+        );
+
+        $productService->get($productSku);
+    }
+
+    public function testCreate()
+    {
+        $initializationHelper = $this
+            ->getMockBuilder('Magento\Catalog\Controller\Adminhtml\Product\Initialization\Helper')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $productMapper = $this
+            ->getMockBuilder('Magento\Catalog\Service\V1\Data\ProductMapper')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $productTypeManager = $this
+            ->getMockBuilder('Magento\Catalog\Model\Product\TypeTransitionManager')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        /** @var \Magento\Catalog\Service\V1\ProductService $productService */
+        $productService = $this->_objectManager->getObject(
+            'Magento\Catalog\Service\V1\ProductService',
+            [
+                'initializationHelper' => $initializationHelper,
+                'productMapper' => $productMapper,
+                'productTypeManager' => $productTypeManager,
+                'productLoader' => $this->_productLoaderMock,
+            ]
+        );
+
+        $productModel = $this->getMockBuilder('Magento\Catalog\Model\Product')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $product = $this->getMockBuilder('Magento\Catalog\Service\V1\Data\Product')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $productMapper->expects($this->once())->method('toModel')->with($product)
+            ->will($this->returnValue($productModel));
+
+        $initializationHelper->expects($this->once())->method('initialize')->with($productModel);
+
+        $productModel->expects($this->once())->method('validate');
+        $productModel->expects($this->once())->method('save');
+
+        $productSku = 'sku-001';
+        $productModel->expects($this->once())->method('getId')->will($this->returnValue(100));
+        $productModel->expects($this->once())->method('getSku')->will($this->returnValue($productSku));
+
+        $this->assertEquals($productSku, $productService->create($product));
+    }
+
+    public function testUpdate()
+    {
+        $initializationHelper = $this
+            ->getMockBuilder('Magento\Catalog\Controller\Adminhtml\Product\Initialization\Helper')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $productMapper = $this
+            ->getMockBuilder('Magento\Catalog\Service\V1\Data\ProductMapper')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $productTypeManager = $this
+            ->getMockBuilder('Magento\Catalog\Model\Product\TypeTransitionManager')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $productLoader = $this
+            ->getMockBuilder('Magento\Catalog\Service\V1\Product\ProductLoader')
+            ->setMethods(['load'])
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        /** @var \Magento\Catalog\Service\V1\ProductService $productService */
+        $productService = $this->_objectManager->getObject(
+            'Magento\Catalog\Service\V1\ProductService',
+            [
+                'initializationHelper' => $initializationHelper,
+                'productMapper' => $productMapper,
+                'productTypeManager' => $productTypeManager,
+                'productLoader' => $productLoader,
+            ]
+        );
+
+        $productModel = $this->getMockBuilder('Magento\Catalog\Model\Product')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $product = $this->getMockBuilder('Magento\Catalog\Service\V1\Data\Product')
+            ->disableOriginalConstructor()
+            ->getMock();
+        $productLoader->expects($this->once())->method('load')
+            ->will($this->returnValue($productModel));
+
+        $productMapper->expects($this->once())->method('toModel')->with($product, $productModel)
+            ->will($this->returnValue($productModel));
+
+        $initializationHelper->expects($this->once())->method('initialize')->with($productModel);
+        $productTypeManager->expects($this->once())->method('processProduct')->with($productModel);
+
+        $productModel->expects($this->once())->method('validate');
+        $productModel->expects($this->once())->method('save');
+
+        $productSku = 'sku-001';
+        $productModel->expects($this->any())->method('getSku')->will($this->returnValue($productSku));
+
+        $this->assertEquals($productSku, $productService->update(5, $product));
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/CatalogInventory/Block/QtyincrementsTest.php b/dev/tests/unit/testsuite/Magento/CatalogInventory/Block/QtyincrementsTest.php
index 413eb2afe69..c84beb18cda 100644
--- a/dev/tests/unit/testsuite/Magento/CatalogInventory/Block/QtyincrementsTest.php
+++ b/dev/tests/unit/testsuite/Magento/CatalogInventory/Block/QtyincrementsTest.php
@@ -23,6 +23,9 @@
  */
 namespace Magento\CatalogInventory\Block;
 
+/**
+ * Unit test for Qtyincrements block
+ */
 class QtyincrementsTest extends \PHPUnit_Framework_TestCase
 {
     /**
@@ -35,14 +38,23 @@ class QtyincrementsTest extends \PHPUnit_Framework_TestCase
      */
     protected $registryMock;
 
+    /**
+     * @var \Magento\CatalogInventory\Service\V1\StockItem|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $stockItemService;
+
     protected function setUp()
     {
         $objectManager = new \Magento\TestFramework\Helper\ObjectManager($this);
-        $this->registryMock = $this->getMock('Magento\Framework\Registry', array(), array(), '', false);
+        $this->registryMock = $this->getMock('Magento\Framework\Registry', [], [], '', false);
+        $this->stockItemService = $this->getMock('Magento\CatalogInventory\Service\V1\StockItem', [], [], '', false);
 
         $this->block = $objectManager->getObject(
             'Magento\CatalogInventory\Block\Qtyincrements',
-            array('registry' => $this->registryMock)
+            [
+                'registry' => $this->registryMock,
+                'stockItemService' => $this->stockItemService
+            ]
         );
     }
 
@@ -54,17 +66,51 @@ class QtyincrementsTest extends \PHPUnit_Framework_TestCase
     public function testGetIdentities()
     {
         $productTags = array('catalog_product_1');
-        $product = $this->getMock('Magento\Catalog\Model\Product', array(), array(), '', false);
+        $product = $this->getMock('Magento\Catalog\Model\Product', [], [], '', false);
         $product->expects($this->once())->method('getIdentities')->will($this->returnValue($productTags));
-        $this->registryMock->expects(
-            $this->once()
-        )->method(
-            'registry'
-        )->with(
-            'current_product'
-        )->will(
-            $this->returnValue($product)
-        );
+        $this->registryMock->expects($this->once())
+            ->method('registry')
+            ->with('current_product')
+            ->will($this->returnValue($product));
         $this->assertEquals($productTags, $this->block->getIdentities());
     }
+
+    /**
+     * @param int $productId
+     * @param int $qtyInc
+     * @param bool $isSaleable
+     * @param int|bool $result
+     * @dataProvider getProductQtyIncrementsDataProvider
+     */
+    public function testGetProductQtyIncrements($productId, $qtyInc, $isSaleable, $result)
+    {
+        $this->stockItemService->expects($this->once())
+            ->method('getQtyIncrements')
+            ->with($this->equalTo($productId))
+            ->will($this->returnValue($qtyInc));
+
+        $product = $this->getMock('Magento\Catalog\Model\Product', [], [], '', false);
+        $product->expects($this->once())->method('getId')->will($this->returnValue($productId));
+        $product->expects($this->once())->method('isSaleable')->will($this->returnValue($isSaleable));
+
+        $this->registryMock->expects($this->any())
+            ->method('registry')
+            ->with('current_product')
+            ->will($this->returnValue($product));
+
+        $this->assertSame($result, $this->block->getProductQtyIncrements());
+        // test lazy load
+        $this->assertSame($result, $this->block->getProductQtyIncrements());
+    }
+
+    /**
+     * @return array
+     */
+    public function getProductQtyIncrementsDataProvider()
+    {
+        return [
+            [1, 100, true, 100],
+            [1, 100, false, false],
+        ];
+    }
 }
diff --git a/dev/tests/unit/testsuite/Magento/CatalogInventory/Block/Stockqty/DefaultStockqtyTest.php b/dev/tests/unit/testsuite/Magento/CatalogInventory/Block/Stockqty/DefaultStockqtyTest.php
index 45f0f5d3097..2a54673367f 100644
--- a/dev/tests/unit/testsuite/Magento/CatalogInventory/Block/Stockqty/DefaultStockqtyTest.php
+++ b/dev/tests/unit/testsuite/Magento/CatalogInventory/Block/Stockqty/DefaultStockqtyTest.php
@@ -23,6 +23,9 @@
  */
 namespace Magento\CatalogInventory\Block\Stockqty;
 
+/**
+ * Unit test for DefaultStockqty
+ */
 class DefaultStockqtyTest extends \PHPUnit_Framework_TestCase
 {
     /**
@@ -35,14 +38,20 @@ class DefaultStockqtyTest extends \PHPUnit_Framework_TestCase
      */
     protected $registryMock;
 
+    /**
+     * @var \Magento\CatalogInventory\Service\V1\StockItem|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $stockItemService;
+
     protected function setUp()
     {
         $objectManager = new \Magento\TestFramework\Helper\ObjectManager($this);
         $this->registryMock = $this->getMock('Magento\Framework\Registry', array(), array(), '', false);
+        $this->stockItemService = $this->getMock('Magento\CatalogInventory\Service\V1\StockItem', [], [], '', false);
 
         $this->block = $objectManager->getObject(
             'Magento\CatalogInventory\Block\Stockqty\DefaultStockqty',
-            array('registry' => $this->registryMock)
+            array('registry' => $this->registryMock, 'stockItemService' => $this->stockItemService)
         );
     }
 
@@ -56,15 +65,82 @@ class DefaultStockqtyTest extends \PHPUnit_Framework_TestCase
         $productTags = array('catalog_product_1');
         $product = $this->getMock('Magento\Catalog\Model\Product', array(), array(), '', false);
         $product->expects($this->once())->method('getIdentities')->will($this->returnValue($productTags));
-        $this->registryMock->expects(
-            $this->once()
-        )->method(
-            'registry'
-        )->with(
-            'current_product'
-        )->will(
-            $this->returnValue($product)
-        );
+        $this->registryMock->expects($this->once())
+            ->method('registry')
+            ->with('current_product')
+            ->will($this->returnValue($product));
         $this->assertEquals($productTags, $this->block->getIdentities());
     }
+
+    /**
+     * @param int $productStockQty
+     * @param int|null $productId
+     * @param int|null $dataQty
+     * @param int $expectedQty
+     * @dataProvider getStockQtyDataProvider
+     */
+    public function testGetStockQty($productStockQty, $productId, $dataQty, $expectedQty)
+    {
+        $this->assertNull($this->block->getData('product_stock_qty'));
+        if ($dataQty) {
+            $this->setDataArrayValue('product_stock_qty', $dataQty);
+        } else {
+            $product = $this->getMock('Magento\Catalog\Model\Product', ['getId', '__wakeup'], [], '', false);
+            $product->expects($this->any())->method('getId')->will($this->returnValue($productId));
+
+            $this->registryMock->expects($this->any())
+                ->method('registry')
+                ->with('current_product')
+                ->will($this->returnValue($product));
+
+            if ($productId) {
+                $this->stockItemService->expects($this->once())
+                    ->method('getStockQty')
+                    ->with($this->equalTo($productId))
+                    ->will($this->returnValue($productStockQty));
+            }
+        }
+        $this->assertSame($expectedQty, $this->block->getStockQty());
+        $this->assertSame($expectedQty, $this->block->getData('product_stock_qty'));
+    }
+
+    /**
+     * @return array
+     */
+    public function getStockQtyDataProvider()
+    {
+        return [
+            [
+                'product qty' => 100,
+                'product id' => 5,
+                'default qty' => null,
+                'expected qty' => 100
+            ],
+            [
+                'product qty' => 100,
+                'product id' => null,
+                'default qty' => null,
+                'expected qty' => 0
+            ],
+            [
+                'product qty' => null,
+                'product id' => null,
+                'default qty' => 50,
+                'expected qty' => 50
+            ],
+        ];
+    }
+
+    /**
+     * @param string $key
+     * @param string|float|int $value
+     */
+    protected function setDataArrayValue($key, $value)
+    {
+        $property = new \ReflectionProperty($this->block, '_data');
+        $property->setAccessible(true);
+        $dataArray = $property->getValue($this->block);
+        $dataArray[$key] = $value;
+        $property->setValue($this->block, $dataArray);
+    }
 }
diff --git a/dev/tests/unit/testsuite/Magento/CatalogInventory/Model/Stock/ItemTest.php b/dev/tests/unit/testsuite/Magento/CatalogInventory/Model/Stock/ItemTest.php
index 88b8b45ae57..1a209a447ce 100644
--- a/dev/tests/unit/testsuite/Magento/CatalogInventory/Model/Stock/ItemTest.php
+++ b/dev/tests/unit/testsuite/Magento/CatalogInventory/Model/Stock/ItemTest.php
@@ -23,26 +23,48 @@
  */
 namespace Magento\CatalogInventory\Model\Stock;
 
+use Magento\TestFramework\Helper\ObjectManager as ObjectManagerHelper;
+
 /**
  * Class ItemTest
+ *
+ * @SuppressWarnings(PHPMD.CouplingBetweenObjects)
  */
 class ItemTest extends \PHPUnit_Framework_TestCase
 {
+    /** @var ObjectManagerHelper */
+    protected $objectManagerHelper;
+
     /**
      * @var \Magento\CatalogInventory\Model\Stock\Item
      */
     protected $item;
 
     /**
-     * @var \Magento\CatalogInventory\Model\Resource\Stock\Item | \PHPUnit_Framework_MockObject_MockObject
+     * @var \Magento\CatalogInventory\Model\Resource\Stock\Item|\PHPUnit_Framework_MockObject_MockObject
      */
     protected $resource;
 
     /**
-     * @var \Magento\Framework\Event\Manager | \PHPUnit_Framework_MockObject_MockObject
+     * @var \Magento\Framework\Event\Manager|\PHPUnit_Framework_MockObject_MockObject
      */
     protected $eventManager;
 
+    /** @var \Magento\Catalog\Model\Product|\PHPUnit_Framework_MockObject_MockObject */
+    protected $product;
+
+    /** @var \Magento\Framework\App\Config|\PHPUnit_Framework_MockObject_MockObject */
+    protected $scopeConfig;
+
+    /** @var \Magento\Customer\Model\Session|\PHPUnit_Framework_MockObject_MockObject */
+    protected $customerSession;
+
+    /** @var \Magento\CatalogInventory\Helper\Minsaleqty|\PHPUnit_Framework_MockObject_MockObject */
+    protected $catalogInventoryMinsaleqty;
+
+    /** @var \Magento\Store\Model\StoreManagerInterface|\PHPUnit_Framework_MockObject_MockObject */
+    protected $storeManager;
+
     protected function setUp()
     {
         $this->resource = $this->getMock(
@@ -66,16 +88,38 @@ class ItemTest extends \PHPUnit_Framework_TestCase
             '',
             false
         );
+        $this->customerSession = $this->getMock('Magento\Customer\Model\Session', [], [], '', false);
         $context->expects($this->any())
             ->method('getEventDispatcher')
             ->will($this->returnValue($this->eventManager));
 
-        $objectManager = new \Magento\TestFramework\Helper\ObjectManager($this);
-        $this->item = $objectManager->getObject(
+        $this->product = $this->getMock('Magento\Catalog\Model\Product', [], [], '', false);
+        $productFactory = $this->getMock('Magento\Catalog\Model\ProductFactory', ['create'], [], '', false);
+        $productFactory->expects($this->any())
+            ->method('create')
+            ->will($this->returnValue($this->product));
+
+        $this->catalogInventoryMinsaleqty = $this->getMock(
+            'Magento\CatalogInventory\Helper\Minsaleqty',
+            [],
+            [],
+            '',
+            false
+        );
+        $this->scopeConfig = $this->getMock('Magento\Framework\App\Config', [], [], '', false);
+        $this->storeManager = $this->getMock('Magento\Store\Model\StoreManagerInterface', [], [], '', false);
+
+        $this->objectManagerHelper = new ObjectManagerHelper($this);
+        $this->item = $this->objectManagerHelper->getObject(
             'Magento\CatalogInventory\Model\Stock\Item',
             [
-                'resource' => $this->resource,
-                'context' => $context
+                'context' => $context,
+                'customerSession' => $this->customerSession,
+                'catalogInventoryMinsaleqty' => $this->catalogInventoryMinsaleqty,
+                'scopeConfig' => $this->scopeConfig,
+                'storeManager' => $this->storeManager,
+                'productFactory' => $productFactory,
+                'resource' => $this->resource
             ]
         );
     }
@@ -96,11 +140,527 @@ class ItemTest extends \PHPUnit_Framework_TestCase
             ->method('dispatch')
             ->with('cataloginventory_stock_item_save_before', ['data_object' => $this->item, 'item' => $this->item]);
 
-
         $this->resource->expects($this->once())
             ->method('addCommitCallback')
             ->will($this->returnValue($this->resource));
 
         $this->assertEquals($this->item, $this->item->save());
     }
+
+    /**
+     * @param array $productConfig
+     * @param array $stockConfig
+     * @param float $expectedQty
+     * @dataProvider getStockQtyDataProvider
+     */
+    public function testGetStockQty($productConfig, $stockConfig, $expectedQty)
+    {
+        $productId = $productConfig['product_id'];
+        $isComposite = $productConfig['is_composite'];
+        $qty = $productConfig['qty'];
+        $useConfigManageStock = $stockConfig['use_config_manage_stock'];
+        $manageStock = $stockConfig['manage_stock'];
+        $isInStock = $productConfig['is_in_stock'];
+        $isSaleable = $productConfig['is_saleable'];
+
+        $this->setDataArrayValue('product_id', $productId);
+        $this->product->expects($this->once())
+            ->method('load')
+            ->with($this->equalTo($productId), $this->equalTo(null))
+            ->will($this->returnSelf());
+
+        $this->product->expects($this->once())
+            ->method('isComposite')
+            ->will($this->returnValue($isComposite));
+
+        $this->setDataArrayValue('qty', $qty);
+        $this->setDataArrayValue('is_in_stock', $isInStock);
+
+        if ($qty > 0 || $manageStock || $isInStock) {
+            $this->product->expects($this->any())
+                ->method('isSaleable')
+                ->will($this->returnValue($isSaleable));
+
+        }
+
+        if ($isComposite) {
+            $this->prepareNotCompositeProductMock();
+        }
+
+        $this->initManageStock($useConfigManageStock, $manageStock);
+        $this->assertSame($expectedQty, $this->item->getStockQty());
+    }
+
+    protected function prepareNotCompositeProductMock()
+    {
+        $productGroup = [
+            [$this->getGroupProductMock(), $this->getGroupProductMock(), $this->getGroupProductMock()],
+            [$this->getGroupProductMock(), $this->getGroupProductMock()],
+        ];
+
+        $typeInstance = $this->getMock(
+            'Magento\Catalog\Model\Product\Type\Simple',
+            ['getProductsToPurchaseByReqGroups'],
+            [],
+            '',
+            false
+        );
+        $typeInstance->expects($this->once())
+            ->method('getProductsToPurchaseByReqGroups')
+            ->with($this->equalTo($this->product))
+            ->will($this->returnValue($productGroup));
+
+        $this->product->expects($this->once())
+            ->method('getTypeInstance')
+            ->will($this->returnValue($typeInstance));
+    }
+
+    /**
+     * @return \PHPUnit_Framework_MockObject_MockObject
+     */
+    protected function getGroupProductMock()
+    {
+        $product = $this->getMock(
+            'Magento\Catalog\Model\Product',
+            ['hasStockItem', 'getStockItem', 'getStockQty', '__wakeup'],
+            [],
+            '',
+            false
+        );
+        $product->expects($this->once())
+            ->method('hasStockItem')
+            ->will($this->returnValue(true));
+        $product->expects($this->once())
+            ->method('getStockItem')
+            ->will($this->returnSelf());
+        $product->expects($this->once())
+            ->method('getStockQty')
+            ->will($this->returnValue(2));
+        return $product;
+    }
+
+    /**
+     * @param string $key
+     * @param string|float|int $value
+     */
+    protected function setDataArrayValue($key, $value)
+    {
+        $property = new \ReflectionProperty($this->item, '_data');
+        $property->setAccessible(true);
+        $dataArray = $property->getValue($this->item);
+        $dataArray[$key] = $value;
+        $property->setValue($this->item, $dataArray);
+    }
+
+    /**
+     * @param bool $useConfigManageStock
+     * @param int $manageStock
+     */
+    protected function initManageStock($useConfigManageStock, $manageStock)
+    {
+        $this->setDataArrayValue('use_config_manage_stock', $useConfigManageStock);
+        if ($useConfigManageStock) {
+            $this->scopeConfig->expects($this->any())
+                ->method('isSetFlag')
+                ->with(
+                    $this->equalTo(Item::XML_PATH_MANAGE_STOCK),
+                    $this->equalTo(\Magento\Store\Model\ScopeInterface::SCOPE_STORE)
+                )
+                ->will($this->returnValue($manageStock));
+        } else {
+            $this->setDataArrayValue('manage_stock', $manageStock);
+        }
+    }
+
+    /**
+     * @return array
+     */
+    public function getStockQtyDataProvider()
+    {
+        return [
+            'composite in stock' => [
+                'product config' => [
+                    'product_id' => 1,
+                    'is_composite' => false,
+                    'qty' => 5.5,
+                    'is_in_stock' => true,
+                    'is_saleable' => true
+                ],
+                'stock config' => ['use_config_manage_stock' => true, 'manage_stock' => true],
+                'expected qty' => 5.5
+            ],
+            'composite not managed' => [
+                'product config' => [
+                    'product_id' => 1,
+                    'is_composite' => false,
+                    'qty' => 2.5,
+                    'is_in_stock' => true,
+                    'is_saleable' => true
+                ],
+                'stock config' => ['use_config_manage_stock' => false, 'manage_stock' => false],
+                'expected qty' => 0.
+            ],
+            'not composite in stock' => [
+                'product config' => [
+                    'product_id' => 1,
+                    'is_composite' => true,
+                    'qty' => 5.5,
+                    'is_in_stock' => true,
+                    'is_saleable' => true
+                ],
+                'stock config' => ['use_config_manage_stock' => true, 'manage_stock' => true],
+                'expected qty' => 4.
+            ],
+            'not composite not saleable' => [
+                'product config' => [
+                    'product_id' => 1,
+                    'is_composite' => true,
+                    'qty' => 5.5,
+                    'is_in_stock' => true,
+                    'is_saleable' => false
+                ],
+                'stock config' => ['use_config_manage_stock' => true, 'manage_stock' => true],
+                'expected qty' => 0.
+            ],
+        ];
+    }
+
+    public function testSetProduct()
+    {
+        $product = $this->getMock(
+            'Magento\Catalog\Model\Product',
+            [
+                'getId',
+                'getName',
+                'getStoreId',
+                'getTypeId',
+                'dataHasChangedFor',
+                'getIsChangedWebsites',
+                '__wakeup'],
+            [],
+            '',
+            false
+        );
+        $productId = 2;
+        $productName = 'Some Name';
+        $storeId = 3;
+        $typeId = 'simple';
+        $status = 1;
+        $isChangedWebsites = false;
+        $product->expects($this->once())->method('getId')->will($this->returnValue($productId));
+        $product->expects($this->once())->method('getName')->will($this->returnValue($productName));
+        $product->expects($this->once())->method('getStoreId')->will($this->returnValue($storeId));
+        $product->expects($this->once())->method('getTypeId')->will($this->returnValue($typeId));
+        $product->expects($this->once())->method('dataHasChangedFor')
+            ->with($this->equalTo('status'))->will($this->returnValue($status));
+        $product->expects($this->once())->method('getIsChangedWebsites')->will($this->returnValue($isChangedWebsites));
+
+        $this->assertSame($this->item, $this->item->setProduct($product));
+        $this->assertSame(
+            [
+                'product_id' => 2,
+                'product_name' => 'Some Name',
+                'store_id' => 3,
+                'product_type_id' => 'simple',
+                'product_status_changed' => 1,
+                'product_changed_websites' => false,
+            ],
+            $this->item->getData()
+        );
+    }
+
+    public function testSetProcessIndexEvents()
+    {
+        $property = new \ReflectionProperty($this->item, '_processIndexEvents');
+        $property->setAccessible(true);
+        $this->assertTrue($property->getValue($this->item));
+        $this->assertSame($this->item, $this->item->setProcessIndexEvents(false));
+        $this->assertFalse($property->getValue($this->item));
+        $this->assertSame($this->item, $this->item->setProcessIndexEvents());
+        $this->assertTrue($property->getValue($this->item));
+    }
+
+    /**
+     * @param array $config
+     * @param bool $expected
+     * @dataProvider verifyNotificationDataProvider
+     */
+    public function testVerifyNotification($config, $expected)
+    {
+        $qty = $config['qty'];
+        $defaultQty = $config['default_qty'];
+        $useConfigNotifyStockQty = $config['use_config_notify_stock_qty'];
+        $notifyStockQty = $config['notify_stock_qty'];
+
+        $this->setDataArrayValue('qty', $defaultQty);
+        $this->setDataArrayValue('use_config_notify_stock_qty', $useConfigNotifyStockQty);
+
+        if ($useConfigNotifyStockQty) {
+            $this->scopeConfig->expects($this->any())
+                ->method('getValue')
+                ->with(
+                    $this->equalTo(Item::XML_PATH_NOTIFY_STOCK_QTY),
+                    $this->equalTo(\Magento\Store\Model\ScopeInterface::SCOPE_STORE)
+                )
+                ->will($this->returnValue($notifyStockQty));
+        } else {
+            $this->setDataArrayValue('notify_stock_qty', $notifyStockQty);
+        }
+
+        $this->assertSame($expected, $this->item->verifyNotification($qty));
+    }
+
+    /**
+     * @return array
+     */
+    public function verifyNotificationDataProvider()
+    {
+        return [
+            [
+                [
+                    'qty' => null,
+                    'default_qty' => 2,
+                    'use_config_notify_stock_qty' => true,
+                    'notify_stock_qty' => 3,
+                ],
+                true
+            ],
+            [
+                [
+                    'qty' => null,
+                    'default_qty' => 3,
+                    'use_config_notify_stock_qty' => true,
+                    'notify_stock_qty' => 3,
+                ],
+                false
+            ],
+            [
+                [
+                    'qty' => 3,
+                    'default_qty' => 3,
+                    'use_config_notify_stock_qty' => false,
+                    'notify_stock_qty' => 3,
+                ],
+                false
+            ],
+            [
+                [
+                    'qty' => 2,
+                    'default_qty' => 3,
+                    'use_config_notify_stock_qty' => false,
+                    'notify_stock_qty' => 3,
+                ],
+                true
+            ],
+        ];
+    }
+
+    /**
+     * @param array $config
+     * @param float $expected
+     * @dataProvider getMaxSaleQtyDataProvider
+     */
+    public function testGetMaxSaleQty($config, $expected)
+    {
+        $useConfigMaxSaleQty = $config['use_config_max_sale_qty'];
+        $maxSaleQty = $config['max_sale_qty'];
+
+        $this->setDataArrayValue('use_config_max_sale_qty', $useConfigMaxSaleQty);
+        if ($useConfigMaxSaleQty) {
+            $this->scopeConfig->expects($this->any())
+                ->method('getValue')
+                ->with(
+                    $this->equalTo(Item::XML_PATH_MAX_SALE_QTY),
+                    $this->equalTo(\Magento\Store\Model\ScopeInterface::SCOPE_STORE)
+                )
+                ->will($this->returnValue($maxSaleQty));
+        } else {
+            $this->setDataArrayValue('max_sale_qty', $maxSaleQty);
+        }
+        $this->assertSame($expected, $this->item->getMaxSaleQty());
+    }
+
+    /**
+     * @return array
+     */
+    public function getMaxSaleQtyDataProvider()
+    {
+        return [
+            [
+                [
+                    'use_config_max_sale_qty' => true,
+                    'max_sale_qty' => 5.,
+                ],
+                5.
+            ],
+            [
+                [
+                    'use_config_max_sale_qty' => false,
+                    'max_sale_qty' => 2.,
+                ],
+                2.
+            ]
+        ];
+    }
+
+    public function testGetAndSetCustomerGroupId()
+    {
+        $groupId = 5;
+        $propertyGroupId = 6;
+        $setValue = 8;
+        $this->customerSession->expects($this->once())
+            ->method('getCustomerGroupId')
+            ->will($this->returnValue($groupId));
+
+        $property = new \ReflectionProperty($this->item, '_customerGroupId');
+        $property->setAccessible(true);
+
+        $this->assertNull($property->getValue($this->item));
+        $this->assertSame($groupId, $this->item->getCustomerGroupId());
+        $this->assertNull($property->getValue($this->item));
+
+        $property->setValue($this->item, $propertyGroupId);
+        $this->assertSame($propertyGroupId, $property->getValue($this->item));
+        $this->assertSame($propertyGroupId, $this->item->getCustomerGroupId());
+
+        $this->assertSame($this->item, $this->item->setCustomerGroupId($setValue));
+        $this->assertSame($setValue, $property->getValue($this->item));
+        $this->assertSame($setValue, $this->item->getCustomerGroupId());
+
+    }
+
+    /**
+     * @param array $config
+     * @param float $expected
+     * @dataProvider getMinSaleQtyDataProvider
+     */
+    public function testGetMinSaleQty($config, $expected)
+    {
+        $groupId = $config['customer_group_id'];
+        $useConfigMinSaleQty = $config['use_config_min_sale_qty'];
+        $minSaleQty = $config['min_sale_qty'];
+
+        $property = new \ReflectionProperty($this->item, '_customerGroupId');
+        $property->setAccessible(true);
+        $property->setValue($this->item, $groupId);
+
+        $property = new \ReflectionProperty($this->item, '_minSaleQtyCache');
+        $property->setAccessible(true);
+        $this->assertEmpty($property->getValue($this->item));
+        $this->setDataArrayValue('use_config_min_sale_qty', $useConfigMinSaleQty);
+
+        if ($useConfigMinSaleQty) {
+            $this->catalogInventoryMinsaleqty->expects($this->once())
+                ->method('getConfigValue')
+                ->with($this->equalTo($groupId))
+                ->will($this->returnValue($minSaleQty));
+        } else {
+            $this->setDataArrayValue('min_sale_qty', $minSaleQty);
+        }
+
+        $this->assertSame($expected, $this->item->getMinSaleQty());
+        // check lazy load
+        $this->assertSame($expected, $this->item->getMinSaleQty());
+    }
+
+    /**
+     * @return array
+     */
+    public function getMinSaleQtyDataProvider()
+    {
+        return [
+            'config value' => [
+                [
+                    'customer_group_id' => 2,
+                    'use_config_min_sale_qty' => true,
+                    'min_sale_qty' => 5.,
+                ],
+                5.
+            ],
+            'object value' => [
+                [
+                    'customer_group_id' => 2,
+                    'use_config_min_sale_qty' => false,
+                    'min_sale_qty' => 3.,
+                ],
+                3.
+            ],
+            'null value' => [
+                [
+                    'customer_group_id' => 2,
+                    'use_config_min_sale_qty' => false,
+                    'min_sale_qty' => null,
+                ],
+                null
+            ],
+        ];
+    }
+
+    /**
+     * @param bool $useConfigMinQty
+     * @param float $minQty
+     * @dataProvider setMinQtyDataProvider
+     */
+    public function testSetMinQty($useConfigMinQty, $minQty)
+    {
+        $this->setDataArrayValue('use_config_min_qty', $useConfigMinQty);
+        if ($useConfigMinQty) {
+            $this->scopeConfig->expects($this->any())
+                ->method('getValue')
+                ->with(
+                    $this->equalTo(Item::XML_PATH_MIN_QTY),
+                    $this->equalTo(\Magento\Store\Model\ScopeInterface::SCOPE_STORE)
+                )
+                ->will($this->returnValue($minQty));
+        } else {
+            $this->setDataArrayValue('min_qty', $minQty);
+        }
+
+        $this->assertSame($minQty, $this->item->getMinQty());
+    }
+
+    /**
+     * @return array
+     */
+    public function setMinQtyDataProvider()
+    {
+        return [
+            [true, 3.3],
+            [false, 6.3],
+        ];
+    }
+
+    /**
+     * @param int $storeId
+     * @param int $managerStoreId
+     * @param int $expected
+     * @dataProvider getStoreIdDataProvider
+     */
+    public function testGetStoreId($storeId, $managerStoreId, $expected)
+    {
+        if ($storeId) {
+            $this->setDataArrayValue('store_id', $storeId);
+        } else {
+            $storeManager = $this->getMock('Magento\Store\Model\Store', [], [], '', false);
+            $storeManager->expects($this->once())->method('getId')->will($this->returnValue($managerStoreId));
+            $this->storeManager->expects($this->once())->method('getStore')->will($this->returnValue($storeManager));
+        }
+        $this->assertSame($expected, $this->item->getStoreId());
+    }
+
+    /**
+     * @return array
+     */
+    public function getStoreIdDataProvider()
+    {
+        return [
+            [1, null, 1],
+            [null, 2, 2],
+        ];
+    }
+
+    public function testGetStockId()
+    {
+        $this->assertSame(1, $this->item->getStockId());
+    }
 }
diff --git a/dev/tests/unit/testsuite/Magento/CatalogInventory/Service/V1/StockItemTest.php b/dev/tests/unit/testsuite/Magento/CatalogInventory/Service/V1/StockItemTest.php
new file mode 100644
index 00000000000..4e50dc52e00
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/CatalogInventory/Service/V1/StockItemTest.php
@@ -0,0 +1,462 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogInventory\Service\V1;
+
+use Magento\CatalogInventory\Model\Stock\ItemRegistry;
+use Magento\Catalog\Model\ProductTypes\ConfigInterface;
+
+/**
+ * Class StockItemTest
+ */
+class StockItemTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @var StockItem
+     */
+    protected $model;
+
+    /**
+     * @var ItemRegistry|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $stockItemRegistry;
+
+    /**
+     * @var ConfigInterface|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $config;
+
+    /**
+     * @var Data\StockItemBuilder|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $stockItemBuilder;
+
+    protected function setUp()
+    {
+        $this->stockItemRegistry = $this->getMockBuilder('Magento\CatalogInventory\Model\Stock\ItemRegistry')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $this->config = $this->getMockBuilder('Magento\Catalog\Model\ProductTypes\ConfigInterface')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $this->stockItemBuilder = $this->getMockBuilder(
+            'Magento\CatalogInventory\Service\V1\Data\StockItemBuilder'
+        )->disableOriginalConstructor()->getMock();
+
+        $this->model = new StockItem($this->stockItemRegistry, $this->config, $this->stockItemBuilder);
+    }
+
+    public function testGetStockItem()
+    {
+        $productId = 123;
+        $stockItemData = ['some_key' => 'someValue'];
+
+        $stockItemModel = $this->getMockBuilder('Magento\CatalogInventory\Model\Stock\Item')
+            ->disableOriginalConstructor()
+            ->getMock();
+        $stockItemModel->expects($this->once())
+            ->method('getData')
+            ->will($this->returnValue($stockItemData));
+
+        $this->stockItemRegistry->expects($this->once())
+            ->method('retrieve')
+            ->with($productId)
+            ->will($this->returnValue($stockItemModel));
+
+        $this->stockItemBuilder->expects($this->once())
+            ->method('populateWithArray')
+            ->with($stockItemData);
+
+        $stockItemDo = $this->getMockBuilder('Magento\CatalogInventory\Service\V1\Data\StockItem')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $this->stockItemBuilder->expects($this->once())
+            ->method('create')
+            ->will($this->returnValue($stockItemDo));
+
+        $this->assertEquals($stockItemDo, $this->model->getStockItem($productId));
+    }
+
+    public function testSaveStockItem()
+    {
+        $productId = 123;
+        $stockItemData = ['some_key' => 'someValue'];
+
+        $stockItemDo = $this->getMockBuilder('Magento\CatalogInventory\Service\V1\Data\StockItem')
+            ->disableOriginalConstructor()
+            ->getMock();
+        $stockItemDo->expects($this->once())
+            ->method('getProductId')
+            ->will($this->returnValue($productId));
+        $stockItemDo->expects($this->once())
+            ->method('__toArray')
+            ->will($this->returnValue($stockItemData));
+
+        $stockItemModel = $this->getMockBuilder('Magento\CatalogInventory\Model\Stock\Item')
+            ->disableOriginalConstructor()
+            ->getMock();
+        $stockItemModel->expects($this->once())
+            ->method('setData')
+            ->with($stockItemData);
+        $stockItemModel->expects($this->once())
+            ->method('save');
+
+        $this->stockItemRegistry->expects($this->once())
+            ->method('retrieve')
+            ->with($productId)
+            ->will($this->returnValue($stockItemModel));
+
+        $this->assertEquals($this->model, $this->model->saveStockItem($stockItemDo));
+    }
+
+    public function testSubtractQty()
+    {
+        $productId = 123;
+        $qty = 1.5;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('subtractQty')
+            ->with($qty);
+
+        $this->assertEquals($this->model, $this->model->subtractQty($productId, $qty));
+    }
+
+    public function testCanSubtractQty()
+    {
+        $productId = 23;
+        $result = false;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('canSubtractQty')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->canSubtractQty($productId));
+    }
+
+    public function testAddQty()
+    {
+        $productId = 143;
+        $qty = 3.5;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('addQty')
+            ->with($qty);
+
+        $this->assertEquals($this->model, $this->model->addQty($productId, $qty));
+    }
+
+    public function testGetMinQty()
+    {
+        $productId = 53;
+        $result = 3;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getMinQty')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getMinQty($productId));
+    }
+
+    public function testGetMinSaleQty()
+    {
+        $productId = 51;
+        $result = 2;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getMinSaleQty')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getMinSaleQty($productId));
+    }
+
+    public function testGetMaxSaleQty()
+    {
+        $productId = 46;
+        $result = 15;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getMaxSaleQty')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getMaxSaleQty($productId));
+    }
+
+    public function testGetNotifyStockQty()
+    {
+        $productId = 12;
+        $result = 15.3;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getNotifyStockQty')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getNotifyStockQty($productId));
+    }
+
+    public function testEnableQtyIncrements()
+    {
+        $productId = 48;
+        $result = true;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getEnableQtyIncrements')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getEnableQtyIncrements($productId));
+    }
+
+    public function testGetQtyIncrements()
+    {
+        $productId = 25;
+        $result = 15;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getQtyIncrements')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getQtyIncrements($productId));
+    }
+
+    public function testGetBackorders()
+    {
+        $productId = 34;
+        $result = 2;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getBackorders')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getBackorders($productId));
+    }
+
+    public function testGetManageStock()
+    {
+        $productId = 32;
+        $result = 3;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getManageStock')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getManageStock($productId));
+    }
+
+    public function testGetCanBackInStock()
+    {
+        $productId = 59;
+        $result = false;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getCanBackInStock')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getCanBackInStock($productId));
+    }
+
+    public function testCheckQty()
+    {
+        $productId = 143;
+        $qty = 3.5;
+        $result = false;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('checkQty')
+            ->with($qty)
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->checkQty($productId, $qty));
+    }
+
+    public function testSuggestQty()
+    {
+        $productId = 143;
+        $qty = 3.5;
+        $result = true;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('suggestQty')
+            ->with($qty)
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->suggestQty($productId, $qty));
+    }
+
+    public function testCheckQuoteItemQty()
+    {
+        $productId = 143;
+        $qty = 3.5;
+        $summaryQty = 4;
+        $origQty = 1;
+        $result = $this->getMock('Magento\Framework\Object');
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('checkQuoteItemQty')
+            ->with($qty, $summaryQty, $origQty)
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->checkQuoteItemQty($productId, $qty, $summaryQty, $origQty));
+    }
+
+    public function testVerifyStock()
+    {
+        $productId = 143;
+        $qty = 2.5;
+        $result = true;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('verifyStock')
+            ->with($qty)
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->verifyStock($productId, $qty));
+    }
+
+    public function testVerifyNotification()
+    {
+        $productId = 42;
+        $qty = 7.3;
+        $result = true;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('verifyNotification')
+            ->with($qty)
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->verifyNotification($productId, $qty));
+    }
+
+    public function testGetIsInStock()
+    {
+        $productId = 96;
+        $result = false;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getIsInStock')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getIsInStock($productId));
+    }
+
+    public function testGetStockQty()
+    {
+        $productId = 34;
+        $result = 3;
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('getStockQty')
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->getStockQty($productId));
+    }
+
+    public function testCheckQtyIncrements()
+    {
+        $productId = 86;
+        $qty = 6;
+        $result = $this->getMock('Magento\Framework\Object');
+
+        $stockItemModel = $this->getStockItemModel($productId);
+        $stockItemModel->expects($this->once())
+            ->method('checkQtyIncrements')
+            ->with($qty)
+            ->will($this->returnValue($result));
+
+        $this->assertEquals($result, $this->model->checkQtyIncrements($productId, $qty));
+    }
+
+    public function testIsQty()
+    {
+        $configAll = [
+            1 => ['is_qty' => true],
+            2 => ['is_qty' => false],
+            3 => []
+        ];
+        $this->config->expects($this->once())
+            ->method('getAll')
+            ->will($this->returnValue($configAll));
+
+        $this->assertTrue($this->model->isQty(1));
+        $this->assertFalse($this->model->isQty(2));
+        $this->assertFalse($this->model->isQty(3));
+        $this->assertFalse($this->model->isQty(4));
+    }
+
+    public function testGetIsQtyTypeIds()
+    {
+        $configAll = [
+            1 => ['is_qty' => true],
+            2 => ['is_qty' => false],
+            3 => []
+        ];
+        $resultAll = [1 => true, 2 => false, 3 => false];
+        $resultTrue = [1 => true];
+        $resultFalse = [2 => false, 3 => false];
+
+        $this->config->expects($this->once())
+            ->method('getAll')
+            ->will($this->returnValue($configAll));
+
+        $this->assertEquals($resultAll, $this->model->getIsQtyTypeIds());
+        $this->assertEquals($resultTrue, $this->model->getIsQtyTypeIds(true));
+        $this->assertEquals($resultFalse, $this->model->getIsQtyTypeIds(false));
+    }
+
+    /**
+     * @param int $productId
+     * @return \PHPUnit_Framework_MockObject_MockObject
+     */
+    protected function getStockItemModel($productId)
+    {
+        $stockItemModel = $this->getMockBuilder('Magento\CatalogInventory\Model\Stock\Item')
+            ->disableOriginalConstructor()
+            ->getMock();
+        $this->stockItemRegistry->expects($this->once())
+            ->method('retrieve')
+            ->with($productId)
+            ->will($this->returnValue($stockItemModel));
+
+        return $stockItemModel;
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/CatalogInventory/Service/V1/StockStatusServiceTest.php b/dev/tests/unit/testsuite/Magento/CatalogInventory/Service/V1/StockStatusServiceTest.php
new file mode 100644
index 00000000000..456c4e007ab
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/CatalogInventory/Service/V1/StockStatusServiceTest.php
@@ -0,0 +1,70 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogInventory\Service\V1;
+
+use Magento\CatalogInventory\Model\Stock\Status;
+
+/**
+ * Test for Magento\CatalogInventory\Service\V1\StockStatusService
+ */
+class StockStatusServiceTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @param int[] $productIds
+     * @param int $websiteId
+     * @param int $stockId
+     * @param [] $expectedResult
+     * @dataProvider getProductStockStatusDataProvider
+     */
+    public function testGetProductStockStatus($productIds, $websiteId, $stockId, $expectedResult)
+    {
+        // 1 Create mocks
+        $stockStatus = $this->getMockBuilder('Magento\CatalogInventory\Model\Stock\Status')
+            ->disableOriginalConstructor()
+            ->getMock();
+        $model = new StockStatusService($stockStatus);
+
+        // 2. Set expectations
+        $stockStatus->expects($this->once())
+            ->method('getProductStockStatus')
+            ->with($productIds, $websiteId, $stockId)
+            ->will($this->returnValue($expectedResult));
+
+        // 3. Run tested method
+        $result = $model->getProductStockStatus($productIds, $websiteId, $stockId);
+
+        // 5. Compare actual result with expected result
+        $this->assertEquals($expectedResult, $result);
+    }
+
+    /**
+     * @return array
+     */
+    public function getProductStockStatusDataProvider()
+    {
+        return [
+            [[1,2], 3, 4, []],
+        ];
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/CatalogSearch/Helper/DataTest.php b/dev/tests/unit/testsuite/Magento/CatalogSearch/Helper/DataTest.php
new file mode 100644
index 00000000000..a262d043754
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/CatalogSearch/Helper/DataTest.php
@@ -0,0 +1,173 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\CatalogSearch\Helper;
+
+/**
+ * Unit test for \Magento\CatalogSearch\Helper\Data
+ */
+class DataTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @var \Magento\CatalogSearch\Helper\Data|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_model;
+
+    /**
+     * @var \Magento\Framework\App\Helper\Context|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_contextMock;
+
+    /**
+     * @var \Magento\Framework\Stdlib\String|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_stringMock;
+
+    /**
+     * @var \PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_queryFactoryMock;
+
+    /**
+     * @var \Magento\Framework\App\Config\ScopeConfigInterface|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_scopeConfigMock;
+
+    /**
+     * @var \Magento\Framework\Escaper|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_escaperMock;
+
+    /**
+     * @var \Magento\Framework\Filter\FilterManager|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_filterManagerMock;
+
+    /**
+     * @var \Magento\Store\Model\StoreManagerInterface|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_storeManagerMock;
+
+    public function setUp()
+    {
+        $this->_contextMock = $this->getMock('Magento\Framework\App\Helper\Context', [], [], '', false);
+        $this->_stringMock = $this->getMock('Magento\Framework\Stdlib\String');
+        $this->_queryFactoryMock = $this->getMock('Magento\CatalogSearch\Model\QueryFactory', [], [], '', false);
+        $this->_scopeConfigMock = $this->getMock('Magento\Framework\App\Config\ScopeConfigInterface');
+        $this->_escaperMock = $this->getMock('Magento\Framework\Escaper');
+        $this->_filterManagerMock = $this->getMock('Magento\Framework\Filter\FilterManager', [], [], '', false);
+        $this->_storeManagerMock = $this->getMock('Magento\Store\Model\StoreManagerInterface');
+
+        $this->_model = new \Magento\CatalogSearch\Helper\Data(
+            $this->_contextMock,
+            $this->_stringMock,
+            $this->_scopeConfigMock,
+            $this->_queryFactoryMock,
+            $this->_escaperMock,
+            $this->_filterManagerMock,
+            $this->_storeManagerMock
+        );
+    }
+
+    /**
+     * @param null|string $expected
+     * @param array $data
+     * @dataProvider prepareIndexdataDataProvider
+     */
+    public function testPrepareIndexdata($expected, array $data)
+    {
+        $this->assertEquals($expected, $this->_model->prepareIndexdata($data['index'], $data['separator']));
+    }
+
+    public function testGetMinQueryLength()
+    {
+        $return = 'some_value';
+        $this->_scopeConfigMock->expects($this->once())
+            ->method('getValue')
+            ->with(
+                \Magento\CatalogSearch\Model\Query::XML_PATH_MIN_QUERY_LENGTH,
+                \Magento\Store\Model\ScopeInterface::SCOPE_STORE,
+                null
+            )
+            ->will($this->returnValue($return));
+        $this->assertEquals($return, $this->_model->getMinQueryLength());
+    }
+
+    public function testGetMaxQueryLength()
+    {
+        $return = 'some_value';
+        $this->_scopeConfigMock->expects($this->once())
+            ->method('getValue')
+            ->with(
+                \Magento\CatalogSearch\Model\Query::XML_PATH_MAX_QUERY_LENGTH,
+                \Magento\Store\Model\ScopeInterface::SCOPE_STORE,
+                null
+            )
+            ->will($this->returnValue($return));
+        $this->assertEquals($return, $this->_model->getMaxQueryLength());
+    }
+
+    public function testGetMaxQueryWords()
+    {
+        $return = 'some_value';
+        $this->_scopeConfigMock->expects($this->once())
+            ->method('getValue')
+            ->with(
+                \Magento\CatalogSearch\Model\Query::XML_PATH_MAX_QUERY_WORDS,
+                \Magento\Store\Model\ScopeInterface::SCOPE_STORE,
+                null
+            )
+            ->will($this->returnValue($return));
+        $this->assertEquals($return, $this->_model->getMaxQueryWords());
+    }
+
+    /**
+     * @return array
+     */
+    public function prepareIndexdataDataProvider()
+    {
+        return array(
+            array(
+                null,
+                array(
+                    'index' => array(),
+                    'separator' => '--'
+                )
+            ),
+            array(
+                'element1--element2--element3--element4',
+                array(
+                    'index' => array(
+                        'element1',
+                        'element2',
+                        array(
+                            'element3',
+                            'element4',
+                        )
+                    ),
+                    'separator' => '--'
+                )
+            )
+        );
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Checkout/Model/CartTest.php b/dev/tests/unit/testsuite/Magento/Checkout/Model/CartTest.php
new file mode 100644
index 00000000000..aa7e63f09d0
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Checkout/Model/CartTest.php
@@ -0,0 +1,128 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+
+namespace Magento\Checkout\Model;
+
+use Magento\TestFramework\Helper\ObjectManager as ObjectManagerHelper;
+
+/**
+ * Class CartTest
+ */
+class CartTest extends \PHPUnit_Framework_TestCase
+{
+    /** @var \Magento\Checkout\Model\Cart */
+    protected $cart;
+
+    /** @var ObjectManagerHelper */
+    protected $objectManagerHelper;
+
+    /** @var \Magento\Checkout\Model\Session|\PHPUnit_Framework_MockObject_MockObject */
+    protected $checkoutSessionMock;
+
+    /** @var \Magento\CatalogInventory\Service\V1\StockItem|\PHPUnit_Framework_MockObject_MockObject */
+    protected $stockItemMock;
+
+    protected function setUp()
+    {
+        $this->checkoutSessionMock = $this->getMock('Magento\Checkout\Model\Session', [], [], '', false);
+        $this->stockItemMock = $this->getMock('Magento\CatalogInventory\Service\V1\StockItem', [], [], '', false);
+
+        $this->objectManagerHelper = new ObjectManagerHelper($this);
+        $this->cart = $this->objectManagerHelper->getObject(
+            'Magento\Checkout\Model\Cart',
+            [
+                'checkoutSession' => $this->checkoutSessionMock,
+                'stockItemService' => $this->stockItemMock
+            ]
+        );
+    }
+
+    public function testSuggestItemsQty()
+    {
+        $data = [[], ['qty' => -2], ['qty' => 3], ['qty' => 3.5], ['qty' => 5], ['qty' => 4]];
+
+        $quote = $this->getMock('Magento\Sales\Model\Quote', [], [], '', false);
+        $quote->expects($this->any())
+            ->method('getItemById')
+            ->will($this->returnValueMap([
+                [2, $this->prepareQuoteItemMock(2)],
+                [3, $this->prepareQuoteItemMock(3)],
+                [4, $this->prepareQuoteItemMock(4)],
+                [5, $this->prepareQuoteItemMock(5)],
+            ]));
+
+        $this->stockItemMock->expects($this->any())
+            ->method('suggestQty')
+            ->will($this->returnValueMap([[4, 3., 3.], [5, 3.5, 3.5]]));
+
+        $this->checkoutSessionMock->expects($this->once())
+            ->method('getQuote')
+            ->will($this->returnValue($quote));
+
+        $this->assertSame(
+            [
+                [],
+                ['qty' => -2],
+                ['qty' => 3., 'before_suggest_qty' => 3.],
+                ['qty' => 3.5, 'before_suggest_qty' => 3.5],
+                ['qty' => 5],
+                ['qty' => 4],
+            ],
+            $this->cart->suggestItemsQty($data)
+        );
+    }
+
+    /**
+     * @param int|bool $itemId
+     * @return \PHPUnit_Framework_MockObject_MockObject
+     */
+    public function prepareQuoteItemMock($itemId)
+    {
+        switch ($itemId) {
+            case 2:
+                $product = $this->getMock('Magento\Catalog\Model\Product', [], [], '', false);
+                $product->expects($this->once())
+                    ->method('getId')
+                    ->will($this->returnValue(4));
+                break;
+            case 3:
+                $product = $this->getMock('Magento\Catalog\Model\Product', [], [], '', false);
+                $product->expects($this->once())
+                    ->method('getId')
+                    ->will($this->returnValue(5));
+                break;
+            case 4:
+                $product = false;
+                break;
+            default:
+                return false;
+        }
+
+        $quoteItem = $this->getMock('Magento\Sales\Model\Quote\Item', [], [], '', false);
+        $quoteItem->expects($this->once())
+            ->method('getProduct')
+            ->will($this->returnValue($product));
+        return $quoteItem;
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Helper/DataTest.php b/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Helper/DataTest.php
new file mode 100644
index 00000000000..aa6ee397b6d
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Helper/DataTest.php
@@ -0,0 +1,200 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\ConfigurableProduct\Helper;
+
+class DataTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @var \Magento\ConfigurableProduct\Helper\Data|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_model;
+
+    /**
+     * @var \Magento\Catalog\Helper\Image|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_imageHelperMock;
+
+    /**
+     * @var \Magento\Catalog\Model\Product|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_productMock;
+
+    protected function setUp()
+    {
+        $this->_imageHelperMock = $this->getMock('Magento\Catalog\Helper\Image', array(), array(), '', false);
+        $this->_productMock = $this->getMock('Magento\Catalog\Model\Product', array(), array(), '', false);
+
+        $this->_model = new \Magento\ConfigurableProduct\Helper\Data($this->_imageHelperMock);
+    }
+
+    public function testGetAllowAttributes()
+    {
+        $typeInstanceMock = $this->getMock(
+            'Magento\ConfigurableProduct\Model\Product\Type\Configurable', array(), array(), '', false
+        );
+        $typeInstanceMock->expects($this->once())
+            ->method('getConfigurableAttributes')
+            ->with($this->_productMock);
+
+        $this->_productMock->expects($this->once())
+            ->method('getTypeInstance')
+            ->will($this->returnValue($typeInstanceMock));
+
+        $this->_model->getAllowAttributes($this->_productMock);
+    }
+
+    /**
+     * @param array $expected
+     * @param array $data
+     * @dataProvider getOptionsDataProvider
+     */
+    public function testGetOptions(array $expected, array $data)
+    {
+        $this->_imageHelperMock->expects($this->at(0))
+            ->method('init')
+            ->will($this->returnValue('http://example.com/base_img_url'));
+
+        for ($i = 1; $i <= count($data['allowed_products']); $i++) {
+            $this->_imageHelperMock->expects($this->at($i))
+                ->method('init')
+                ->will($this->returnValue('http://example.com/base_img_url_' . $i));
+        }
+
+        $this->assertEquals(
+            $expected,
+            $this->_model->getOptions($data['current_product_mock'], $data['allowed_products'])
+        );
+    }
+
+    /**
+     * @return array
+     */
+    public function getOptionsDataProvider()
+    {
+        $currentProductMock = $this->getMock(
+            'Magento\Catalog\Model\Product', array('getTypeInstance', '__wakeup'), array(), '', false
+        );
+        $provider = array();
+        $provider[] = array(
+            array(),
+            array(
+                'allowed_products' => array(),
+                'current_product_mock' => $currentProductMock
+            )
+        );
+        $attributesCount = 3;
+        $attributes = array();
+        for ($i = 1; $i < $attributesCount; $i++) {
+            $attribute = $this->getMock(
+                'Magento\Framework\Object', array('getProductAttribute'), array(), '', false
+            );
+            $productAttribute = $this->getMock(
+                'Magento\Framework\Object',
+                array('getId', 'getAttributeCode'),
+                array(),
+                '',
+                false
+            );
+            $productAttribute->expects($this->any())
+                ->method('getId')
+                ->will($this->returnValue('attribute_id_' . $i));
+            $productAttribute->expects($this->any())
+                ->method('getAttributeCode')
+                ->will($this->returnValue('attribute_code_' . $i));
+            $attribute->expects($this->any())
+                ->method('getProductAttribute')
+                ->will($this->returnValue($productAttribute));
+            $attributes[] = $attribute;
+        }
+        $typeInstanceMock = $this->getMock(
+            'Magento\ConfigurableProduct\Model\Product\Type\Configurable', array(), array(), '', false
+        );
+        $typeInstanceMock->expects($this->any())
+            ->method('getConfigurableAttributes')
+            ->will($this->returnValue($attributes));
+        $currentProductMock->expects($this->any())
+            ->method('getTypeInstance')
+            ->will($this->returnValue($typeInstanceMock));
+        $allowedProducts = array();
+        for ($i = 1; $i <= 2; $i++) {
+            $productMock = $this->getMock(
+                'Magento\Catalog\Model\Product', array('getData', 'getImage', 'getId', '__wakeup'), array(), '', false
+            );
+            $productMock->expects($this->any())
+                ->method('getData')
+                ->will($this->returnCallback(array($this, 'getDataCallback')));
+            $productMock->expects($this->any())
+                ->method('getId')
+                ->will($this->returnValue('product_id_' . $i));
+            if ($i == 2) {
+                $productMock->expects($this->any())
+                    ->method('getImage')
+                    ->will($this->returnValue(true));
+            }
+            $allowedProducts[] = $productMock;
+        }
+        $provider[] = array(
+            array(
+                'attribute_id_1' => array(
+                    'attribute_code_value_1' => array('product_id_1', 'product_id_2')
+                ),
+                'images' => array(
+                    'attribute_id_1' => array(
+                        'attribute_code_value_1' => array(
+                            'product_id_1' => 'http://example.com/base_img_url',
+                            'product_id_2' => 'http://example.com/base_img_url_2'
+                        )
+                    ),
+                    'attribute_id_2' => array(
+                        'attribute_code_value_2' => array(
+                            'product_id_1' => 'http://example.com/base_img_url',
+                            'product_id_2' => 'http://example.com/base_img_url_2'
+                        )
+                    ),
+                ),
+                'attribute_id_2' => array(
+                    'attribute_code_value_2' => array('product_id_1', 'product_id_2')
+                )
+            ),
+            array(
+                'allowed_products' => $allowedProducts,
+                'current_product_mock' => $currentProductMock
+            )
+        );
+        return $provider;
+    }
+
+    /**
+     * @param string $key
+     * @return string
+     */
+    public function getDataCallback($key)
+    {
+        $map = array();
+        for ($k = 1; $k < 3; $k++) {
+            $map['attribute_code_' . $k] = 'attribute_code_value_' . $k;
+        }
+        return $map[$key];
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Export/RowCustomizerTest.php b/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Export/RowCustomizerTest.php
new file mode 100644
index 00000000000..4fb88f49ccf
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Export/RowCustomizerTest.php
@@ -0,0 +1,236 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\ConfigurableProduct\Model\Export;
+
+class RowCustomizerTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @var \Magento\ConfigurableProduct\Model\Export\RowCustomizer
+     */
+    protected $_model;
+
+    /**
+     * @var \Magento\Catalog\Model\Resource\Product\Collection|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_collectionMock;
+
+    protected function setUp()
+    {
+        $this->_collectionMock = $this->getMock(
+            'Magento\Catalog\Model\Resource\Product\Collection',
+            array('addAttributeToFilter', 'fetchItem', '__wakeup'),
+            array(),
+            '',
+            false
+        );
+        $this->_model = new \Magento\ConfigurableProduct\Model\Export\RowCustomizer;
+    }
+
+    public function testPrepareData()
+    {
+        $this->_initConfigurableData();
+    }
+
+    public function testAddHeaderColumns()
+    {
+        $this->_initConfigurableData();
+        $this->assertEquals(
+            array(
+                'column_1',
+                'column_2',
+                'column_3',
+                '_super_products_sku',
+                '_super_attribute_code',
+                '_super_attribute_option',
+                '_super_attribute_price_corr'
+            ),
+            $this->_model->addHeaderColumns(
+                array('column_1', 'column_2', 'column_3')
+            )
+        );
+    }
+
+    /**
+     * @param array $expected
+     * @param array $data
+     * @dataProvider addDataDataProvider
+     */
+    public function testAddData(array $expected, array $data)
+    {
+        $this->_initConfigurableData();
+        $this->assertEquals(
+            $expected,
+            $this->_model->addData($data['data_row'], $data['product_id'])
+        );
+    }
+
+    /**
+     * @param array $expected
+     * @param array $data
+     * @dataProvider getAdditionalRowsCountDataProvider
+     */
+    public function testGetAdditionalRowsCount(array $expected, array $data)
+    {
+        $this->_initConfigurableData();
+        $this->assertEquals(
+            $expected,
+            $this->_model->getAdditionalRowsCount($data['row_count'], $data['product_id'])
+        );
+    }
+
+    /**
+     * @return array
+     */
+    public function getAdditionalRowsCountDataProvider()
+    {
+        return array(
+            array(
+                array(1, 2, 3),
+                array(
+                    'row_count' => array(1, 2, 3),
+                    'product_id' => 1
+                )
+            ),
+            array(
+                array(1, 2, 3),
+                array(
+                    'row_count' => array(1, 2, 3),
+                    'product_id' => 11
+                )
+            ),
+            array(
+                array(),
+                array(
+                    'row_count' => array(),
+                    'product_id' => 11
+                )
+            )
+        );
+    }
+
+    /**
+     * @return array
+     */
+    public function addDataDataProvider()
+    {
+        return array(
+            array(
+                array(
+                    'key_1' => 'value_1',
+                    'key_2' => 'value_2',
+                    'key_3' => 'value_3'
+                ),
+                array(
+                    'data_row' => array(
+                        'key_1' => 'value_1',
+                        'key_2' => 'value_2',
+                        'key_3' => 'value_3'
+                    ),
+                    'product_id' => 1
+                )
+            ),
+            array(
+                array(
+                    'key_1' => 'value_1',
+                    'key_2' => 'value_2',
+                    'key_3' => 'value_3',
+                    '_super_products_sku' => '_sku_',
+                    '_super_attribute_code' => 'code_of_attribute',
+                    '_super_attribute_option' => 'Option Title',
+                    '_super_attribute_price_corr' => '12345%'
+                ),
+                array(
+                    'data_row' => array(
+                        'key_1' => 'value_1',
+                        'key_2' => 'value_2',
+                        'key_3' => 'value_3'
+                    ),
+                    'product_id' => 11
+                )
+            )
+        );
+    }
+
+    protected function _initConfigurableData()
+    {
+        $productIds = array(1, 2, 3);
+        $attributes = array(
+            array(
+                array(
+                    'pricing_is_percent' => true,
+                    'sku' => '_sku_',
+                    'attribute_code' => 'code_of_attribute',
+                    'option_title' => 'Option Title',
+                    'pricing_value' => 12345,
+                ),
+                array(
+                    'pricing_is_percent' => false,
+                    'sku' => '_sku_',
+                    'attribute_code' => 'code_of_attribute',
+                    'option_title' => 'Option Title',
+                    'pricing_value' => 12345,
+                )
+            )
+        );
+
+        $productMock = $this->getMock(
+            'Magento\Catalog\Model\Product',
+            array('getId', 'getTypeInstance', '__wakeup'),
+            array(),
+            '',
+            false
+        );
+        $productMock->expects($this->any())
+            ->method('getId')
+            ->will($this->returnValue(11));
+
+        $typeInstanceMock = $this->getMock(
+            'Magento\ConfigurableProduct\Model\Product\Type\Configurable', array(), array(), '', false
+        );
+        $typeInstanceMock->expects($this->any())
+            ->method('getConfigurableOptions')
+            ->will($this->returnValue($attributes));
+
+        $productMock->expects($this->any())
+            ->method('getTypeInstance')
+            ->will($this->returnValue($typeInstanceMock));
+
+        $this->_collectionMock->expects($this->at(0))
+            ->method('addAttributeToFilter')
+            ->with('entity_id', array('in' => $productIds))
+            ->will($this->returnSelf());
+        $this->_collectionMock->expects($this->at(1))
+            ->method('addAttributeToFilter')
+            ->with('type_id', array('eq' => \Magento\ConfigurableProduct\Model\Product\Type\Configurable::TYPE_CODE))
+            ->will($this->returnSelf());
+        $this->_collectionMock->expects($this->at(2))
+            ->method('fetchItem')
+            ->will($this->returnValue($productMock));
+        $this->_collectionMock->expects($this->at(3))
+            ->method('fetchItem')
+            ->will($this->returnValue(false));
+
+        $this->_model->prepareData($this->_collectionMock, $productIds);
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Product/Type/ConfigurableTest.php b/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Product/Type/ConfigurableTest.php
index 53f619bd3e2..7912f69c35e 100644
--- a/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Product/Type/ConfigurableTest.php
+++ b/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Product/Type/ConfigurableTest.php
@@ -188,4 +188,49 @@ class ConfigurableTest extends \PHPUnit_Framework_TestCase
 
         $this->_model->save($product);
     }
+
+    public function testGetRelationInfo()
+    {
+        $info = $this->_model->getRelationInfo();
+        $this->assertInstanceOf('Magento\Framework\Object', $info);
+        $this->assertEquals('catalog_product_super_link', $info->getData('table'));
+        $this->assertEquals('parent_id', $info->getData('parent_field_name'));
+        $this->assertEquals('product_id', $info->getData('child_field_name'));
+    }
+
+    public function testCanUseAttribute()
+    {
+        $attribute = $this->getMock(
+            'Magento\Catalog\Model\Resource\Eav\Attribute',
+            array(
+                'getIsGlobal',
+                'getIsVisible',
+                'getIsConfigurable',
+                'usesSource',
+                'getIsUserDefined',
+                '__wakeup',
+                '__sleep'
+            ),
+            array(),
+            '',
+            false
+        );
+        $attribute->expects($this->once())
+            ->method('getIsGlobal')
+            ->will($this->returnValue(1));
+        $attribute->expects($this->once())
+            ->method('getIsVisible')
+            ->will($this->returnValue(1));
+        $attribute->expects($this->once())
+            ->method('getIsConfigurable')
+            ->will($this->returnValue(1));
+        $attribute->expects($this->once())
+            ->method('usesSource')
+            ->will($this->returnValue(1));
+        $attribute->expects($this->once())
+            ->method('getIsUserDefined')
+            ->will($this->returnValue(1));
+
+        $this->assertTrue($this->_model->canUseAttribute($attribute));
+    }
 }
diff --git a/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Product/Type/PluginTest.php b/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Product/Type/PluginTest.php
new file mode 100644
index 00000000000..8288a14716e
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Product/Type/PluginTest.php
@@ -0,0 +1,89 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\ConfigurableProduct\Model\Product\Type;
+
+/**
+ * Class \Magento\ConfigurableProduct\Model\Product\Type\PluginTest
+ */
+class PluginTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @param array $expected
+     * @param array $data
+     * @dataProvider afterGetOptionArrayDataProvider
+     */
+    public function testAfterGetOptionArray(array $expected, array $data)
+    {
+        $moduleManagerMock = $this->getMock(
+            'Magento\Framework\Module\Manager', array('isOutputEnabled'), array(), '', false
+        );
+        $moduleManagerMock->expects($this->once())
+            ->method('isOutputEnabled')
+            ->with('Magento_ConfigurableProduct')
+            ->will($this->returnValue($data['is_module_output_enabled']));
+
+        $model = new \Magento\ConfigurableProduct\Model\Product\Type\Plugin($moduleManagerMock);
+        $this->assertEquals(
+            $expected,
+            $model->afterGetOptionArray($data['subject'], $data['result'])
+        );
+    }
+
+    /**
+     * @return array
+     */
+    public function afterGetOptionArrayDataProvider()
+    {
+        $productTypeMock = $this->getMock('Magento\Catalog\Model\Product\Type', array(), array(), '', false);
+        return array(
+            array(
+                array(
+                    'configurable' => true,
+                    'not_configurable' => true
+                ),
+                array(
+                    'is_module_output_enabled' => true,
+                    'subject' => $productTypeMock,
+                    'result' => array(
+                        'configurable' => true,
+                        'not_configurable' => true
+                    )
+                )
+            ),
+            array(
+                array(
+                    'not_configurable' => true
+                ),
+                array(
+                    'is_module_output_enabled' => false,
+                    'subject' => $productTypeMock,
+                    'result' => array(
+                        'configurable' => true,
+                        'not_configurable' => true
+                    )
+                )
+            )
+        );
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Quote/Item/QuantityValidator/Initializer/Option/Plugin/ConfigurableProductTest.php b/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Quote/Item/QuantityValidator/Initializer/Option/Plugin/ConfigurableProductTest.php
new file mode 100644
index 00000000000..c137b2a823b
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/ConfigurableProduct/Model/Quote/Item/QuantityValidator/Initializer/Option/Plugin/ConfigurableProductTest.php
@@ -0,0 +1,95 @@
+<?php
+/**
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\ConfigurableProduct\Model\Quote\Item\QuantityValidator\Initializer\Option\Plugin;
+
+class ConfigurableProductTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @param array $data
+     * @dataProvider beforeInitializeDataProvider
+     */
+    public function testBeforeInitialize(array $data)
+    {
+        $subjectMock = $this->getMock(
+            'Magento\CatalogInventory\Model\Quote\Item\QuantityValidator\Initializer\Option',
+            array(),
+            array(),
+            '',
+            false
+        );
+
+        $quoteItemMock = $this->getMock(
+            'Magento\Sales\Model\Quote\Item', array('getProductType', '__wakeup'), array(), '', false
+        );
+        $quoteItemMock->expects($this->once())
+            ->method('getProductType')
+            ->will($this->returnValue($data['product_type']));
+
+        $stockItemMock = $this->getMock(
+            'Magento\CatalogInventory\Model\Stock\Item', array('setProductName', '__wakeup'), array(), '', false
+        );
+        $matcherMethod = $data['matcher_method'];
+        $stockItemMock->expects($this->$matcherMethod())
+            ->method('setProductName');
+
+        $productMock = $this->getMock(
+            'Magento\Catalog\Model\Product', array('getStockItem', '__wakeup'), array(), '', false
+        );
+        $productMock->expects($this->once())
+            ->method('getStockItem')
+            ->will($this->returnValue($stockItemMock));
+
+        $optionMock = $this->getMock(
+            'Magento\Sales\Model\Quote\Item\Option', array('getProduct', '__wakeup'), array(), '', false
+        );
+        $optionMock->expects($this->once())
+            ->method('getProduct')
+            ->will($this->returnValue($productMock));
+
+        $model = new ConfigurableProduct;
+        $model->beforeInitialize($subjectMock, $optionMock, $quoteItemMock, 0);
+
+    }
+
+    /**
+     * @return array
+     */
+    public function beforeInitializeDataProvider()
+    {
+        return array(
+            array(
+                array(
+                    'product_type' => 'not_configurable',
+                    'matcher_method' => 'never'
+                )
+            ),
+            array(
+                array(
+                    'product_type' => 'configurable',
+                    'matcher_method' => 'once'
+                )
+            )
+        );
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Framework/DB/Adapter/Pdo/MysqlTest.php b/dev/tests/unit/testsuite/Magento/Framework/DB/Adapter/Pdo/MysqlTest.php
index 2294b08e31a..46c23a85d43 100644
--- a/dev/tests/unit/testsuite/Magento/Framework/DB/Adapter/Pdo/MysqlTest.php
+++ b/dev/tests/unit/testsuite/Magento/Framework/DB/Adapter/Pdo/MysqlTest.php
@@ -538,88 +538,4 @@ class MysqlTest extends \PHPUnit_Framework_TestCase
             )
         );
     }
-
-    /**
-     * @dataProvider getForeignKeysProvider
-     * @param string $tableName
-     * @param string $schemaName
-     * @param string $constraint
-     * @param array $expected
-     */
-    public function testGetForeignKeys($tableName, $schemaName, $constraint, $expected)
-    {
-        $constraint = ",\n" . $constraint;
-        $this->_adapter->expects($this->once())
-            ->method('getCreateTable')
-            ->will($this->returnValue($constraint));
-        $this->assertEquals($expected, $this->_adapter->getForeignKeys($tableName, $schemaName));
-    }
-
-    public function getForeignKeysProvider()
-    {
-        return [
-            [
-                'table1',
-                'schema1',
-                'CONSTRAINT `FK_SALES_FLAT_ORDER_CUSTOMER_ID_CUSTOMER_ENTITY_ENTITY_ID` FOREIGN KEY '
-                . '(`customer_id`) REFERENCES `customer_entity` (`entity_id`) ON DELETE SET NULL ON UPDATE CASCADE',
-                [
-                    'FK_SALES_FLAT_ORDER_CUSTOMER_ID_CUSTOMER_ENTITY_ENTITY_ID' => [
-                        'FK_NAME'           => 'FK_SALES_FLAT_ORDER_CUSTOMER_ID_CUSTOMER_ENTITY_ENTITY_ID',
-                        'SCHEMA_NAME'       => 'schema1',
-                        'TABLE_NAME'        => 'table1',
-                        'COLUMN_NAME'       => 'customer_id',
-                        'REF_SHEMA_NAME'    => '',
-                        'REF_TABLE_NAME'    => 'customer_entity',
-                        'REF_COLUMN_NAME'   => 'entity_id',
-                        'ON_DELETE'         => 'SET NULL',
-                        'ON_UPDATE'         => 'CASCADE'
-                    ]
-                ]
-            ],
-            [
-                'table1',
-                'schema1',
-                'CONSTRAINT `FK_SALES_FLAT_ORDER_STORE_ID_STORE_STORE_ID` FOREIGN KEY (`store_id`) '
-                . 'REFERENCES `store` (`store_id`) ON DELETE SET NULL ON UPDATE CASCADE',
-                [
-                    'FK_SALES_FLAT_ORDER_STORE_ID_STORE_STORE_ID' => [
-                        'FK_NAME'           => 'FK_SALES_FLAT_ORDER_STORE_ID_STORE_STORE_ID',
-                        'SCHEMA_NAME'       => 'schema1',
-                        'TABLE_NAME'        => 'table1',
-                        'COLUMN_NAME'       => 'store_id',
-                        'REF_SHEMA_NAME'    => '',
-                        'REF_TABLE_NAME'    => 'store',
-                        'REF_COLUMN_NAME'   => 'store_id',
-                        'ON_DELETE'         => 'SET NULL',
-                        'ON_UPDATE'         => 'CASCADE'
-                    ]
-                ]
-            ],
-            [
-                'table1',
-                'schema1',
-                '`entity_id` int(10) unsigned NOT NULL AUTO_INCREMENT COMMENT \'Entity Id\'',
-                []
-            ],
-            [
-                'table1',
-                'schema1',
-                'CONSTRAINT `refdata_ibfk_1` FOREIGN KEY (`refcol`) REFERENCES `test_ref`.`usefuldata` (`col`)',
-                [
-                    'REFDATA_IBFK_1' => [
-                        'FK_NAME'           => 'refdata_ibfk_1',
-                        'SCHEMA_NAME'       => 'schema1',
-                        'TABLE_NAME'        => 'table1',
-                        'COLUMN_NAME'       => 'refcol',
-                        'REF_SHEMA_NAME'    => 'test_ref',
-                        'REF_TABLE_NAME'    => 'usefuldata',
-                        'REF_COLUMN_NAME'   => 'col',
-                        'ON_DELETE'         => '',
-                        'ON_UPDATE'         => ''
-                    ]
-                ]
-            ],
-        ];
-    }
 }
diff --git a/dev/tests/unit/testsuite/Magento/Framework/DB/Helper/AbstractHelperTest.php b/dev/tests/unit/testsuite/Magento/Framework/DB/Helper/AbstractHelperTest.php
new file mode 100644
index 00000000000..4a05102156e
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Framework/DB/Helper/AbstractHelperTest.php
@@ -0,0 +1,174 @@
+<?php
+/**
+ * \Magento\Framework\DB\Helper\AbstractHelper test case
+ *
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Framework\DB\Helper;
+
+class AbstractHelperTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @var \Magento\Framework\DB\Helper\AbstractHelper|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_model;
+
+    /**
+     * @var \Magento\Framework\App\Resource|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_resourceMock;
+
+    /**
+     * @var \Magento\Framework\DB\Adapter\AdapterInterface|\PHPUnit_Framework_MockObject_MockObject
+     */
+    protected $_adapterMock;
+
+    protected function setUp()
+    {
+        $this->_adapterMock = $this->getMock('Magento\Framework\DB\Adapter\AdapterInterface');
+
+        $this->_resourceMock = $this->getMock('Magento\Framework\App\Resource', array(), array(), '', false);
+        $this->_resourceMock->expects($this->any())
+            ->method('getConnection')
+            ->with('prefix_read')
+            ->will($this->returnValue($this->_adapterMock));
+
+        $this->_model = $this->getMockForAbstractClass(
+            'Magento\Framework\DB\Helper\AbstractHelper',
+            array($this->_resourceMock, 'prefix'),
+            '',
+            true,
+            true,
+            true,
+            array('addLikeEscape')
+        );
+    }
+
+    /**
+     * @param string $expected
+     * @param array $data
+     * @dataProvider escapeLikeValueDataProvider
+     */
+    public function testEscapeLikeValue($expected, array $data)
+    {
+        $this->assertEquals($expected, $this->_model->escapeLikeValue($data['value'], $data['options']));
+    }
+
+    public function testGetCILike()
+    {
+        $field = 'field';
+        $value = 'value';
+        $options = array();
+
+        $this->_adapterMock->expects($this->once())
+            ->method('quoteIdentifier')
+            ->with($field)
+            ->will($this->returnArgument(0));
+
+        $this->_model->expects($this->once())
+            ->method('addLikeEscape')
+            ->with($value, $options)
+            ->will($this->returnArgument(0));
+
+        $result = $this->_model->getCILike($field, $value, $options);
+        $this->assertInstanceOf('Zend_Db_Expr', $result);
+        $this->assertEquals($field . ' LIKE ' . $value, (string)$result);
+    }
+
+    /**
+     * @return array
+     */
+    public function escapeLikeValueDataProvider()
+    {
+        return array(
+            array(
+                '',
+                array(
+                    'value' => '',
+                    'options' => array()
+                )
+            ),
+            array(
+                'LIKE \%string\_end',
+                array(
+                    'value' => 'LIKE %string_end',
+                    'options' => array()
+                )
+            ),
+            array(
+                'LIKE \%string_end',
+                array(
+                    'value' => 'LIKE %string_end',
+                    'options' => array(
+                        'allow_symbol_mask' => true
+                    )
+                )
+            ),
+            array(
+                'LIKE %string\_end',
+                array(
+                    'value' => 'LIKE %string_end',
+                    'options' => array(
+                        'allow_string_mask' => true
+                    )
+                )
+            ),
+            array(
+                'LIKE %string_end',
+                array(
+                    'value' => 'LIKE %string_end',
+                    'options' => array(
+                        'allow_symbol_mask' => true,
+                        'allow_string_mask' => true
+                    )
+                )
+            ),
+            array(
+                '%string%',
+                array(
+                    'value' => 'string',
+                    'options' => array(
+                        'position' => 'any'
+                    )
+                )
+            ),
+            array(
+                'string%',
+                array(
+                    'value' => 'string',
+                    'options' => array(
+                        'position' => 'start'
+                    )
+                )
+            ),
+            array(
+                '%string',
+                array(
+                    'value' => 'string',
+                    'options' => array(
+                        'position' => 'end'
+                    )
+                )
+            )
+        );
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Framework/DB/Tree/NodeTest.php b/dev/tests/unit/testsuite/Magento/Framework/DB/Tree/NodeTest.php
new file mode 100644
index 00000000000..876a1dfd23d
--- /dev/null
+++ b/dev/tests/unit/testsuite/Magento/Framework/DB/Tree/NodeTest.php
@@ -0,0 +1,135 @@
+<?php
+/**
+ * \Magento\Framework\DB\Tree\Node test case
+ *
+ * Magento
+ *
+ * NOTICE OF LICENSE
+ *
+ * This source file is subject to the Open Software License (OSL 3.0)
+ * that is bundled with this package in the file LICENSE.txt.
+ * It is also available through the world-wide-web at this URL:
+ * http://opensource.org/licenses/osl-3.0.php
+ * If you did not receive a copy of the license and are unable to
+ * obtain it through the world-wide-web, please send an email
+ * to license@magentocommerce.com so we can send you a copy immediately.
+ *
+ * DISCLAIMER
+ *
+ * Do not edit or add to this file if you wish to upgrade Magento to newer
+ * versions in the future. If you wish to customize Magento for your
+ * needs please refer to http://www.magentocommerce.com for more information.
+ *
+ * @copyright   Copyright (c) 2014 X.commerce, Inc. (http://www.magentocommerce.com)
+ * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
+ */
+namespace Magento\Framework\DB\Tree;
+
+class NodeTest extends \PHPUnit_Framework_TestCase
+{
+    /**
+     * @param array $data
+     * @param $expectedException
+     * @param $expectedExceptionMessage
+     * @dataProvider constructorDataProvider
+     */
+    public function testConstructorWithInvalidArgumentsThrowsException(
+        array $data,
+        $expectedException,
+        $expectedExceptionMessage
+    ) {
+        $this->setExpectedException($expectedException, $expectedExceptionMessage);
+        new \Magento\Framework\DB\Tree\Node($data['node_data'], $data['keys']);
+    }
+
+    /**
+     * @param array $data
+     * @param string $assertMethod
+     * @dataProvider isParentDataProvider
+     */
+    public function testIsParent(array $data, $assertMethod)
+    {
+        $model = new \Magento\Framework\DB\Tree\Node($data['node_data'], $data['keys']);
+        $this->$assertMethod($model->isParent());
+    }
+
+    /**
+     * @return array
+     */
+    public function isParentDataProvider()
+    {
+        return array(
+            array(
+                array(
+                    'node_data' => array(
+                        'id' => 'id',
+                        'pid' => 'pid',
+                        'level' => 'level',
+                        'right_key' => 10,
+                        'left_key' => 5
+                    ),
+                    'keys' => array(
+                        'id' => 'id',
+                        'pid' => 'pid',
+                        'level' => 'level',
+                        'right' => 'right_key',
+                        'left' => 'left_key'
+                    )
+                ),
+                'assertTrue'
+            ),
+            array(
+                array(
+                    'node_data' => array(
+                        'id' => 'id',
+                        'pid' => 'pid',
+                        'level' => 'level',
+                        'right_key' => 5,
+                        'left_key' => 10
+                    ),
+                    'keys' => array(
+                        'id' => 'id',
+                        'pid' => 'pid',
+                        'level' => 'level',
+                        'right' => 'right_key',
+                        'left' => 'left_key'
+                    )
+                ),
+                'assertFalse'
+            )
+        );
+    }
+
+    /**
+     * @return array
+     */
+    public function constructorDataProvider()
+    {
+        return array(
+            array(
+                array(
+                    'node_data' => null,
+                    'keys' => null
+                ),
+                '\Magento\Framework\DB\Tree\Node\NodeException',
+                'Empty array of node information'
+            ),
+            array(
+                array(
+                    'node_data' => null,
+                    'keys' => true
+                ),
+                '\Magento\Framework\DB\Tree\Node\NodeException',
+                'Empty array of node information'
+            ),
+            array(
+                array(
+                    'node_data' => true,
+                    'keys' => null
+                ),
+                '\Magento\Framework\DB\Tree\Node\NodeException',
+                'Empty keys array'
+            )
+        );
+    }
+}
diff --git a/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/Interpreter/ArrayTypeTest.php b/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/Interpreter/ArrayTypeTest.php
index a4a1c8a2339..0a863371094 100644
--- a/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/Interpreter/ArrayTypeTest.php
+++ b/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/Interpreter/ArrayTypeTest.php
@@ -26,9 +26,9 @@ namespace Magento\Framework\Data\Argument\Interpreter;
 class ArrayTypeTest extends \PHPUnit_Framework_TestCase
 {
     /**
-     * @var \Magento\Framework\Data\Argument\InterpreterInterface
+     * @var \PHPUnit_Framework_MockObject_MockObject|\Magento\Framework\Data\Argument\InterpreterInterface
      */
-    protected $_interpreter;
+    protected $_itemInterpreter;
 
     /**
      * @var ArrayType
@@ -37,8 +37,10 @@ class ArrayTypeTest extends \PHPUnit_Framework_TestCase
 
     protected function setUp()
     {
-        $this->_interpreter = $this->getMockForAbstractClass('Magento\Framework\Data\Argument\InterpreterInterface');
-        $this->_model = new ArrayType($this->_interpreter);
+        $this->_itemInterpreter = $this->getMockForAbstractClass(
+            'Magento\Framework\Data\Argument\InterpreterInterface'
+        );
+        $this->_model = new ArrayType($this->_itemInterpreter);
     }
 
     /**
@@ -54,21 +56,53 @@ class ArrayTypeTest extends \PHPUnit_Framework_TestCase
 
     public function evaluateExceptionDataProvider()
     {
-        return array('no item' => array(array()), 'non-array item' => array(array('item' => 'non-array')));
+        return array(
+            'non-array item' => array(array('item' => 'non-array')),
+        );
+    }
+
+    /**
+     * @param array $input
+     * @param array $expected
+     *
+     * @dataProvider evaluateDataProvider
+     */
+    public function testEvaluate(array $input, array $expected)
+    {
+        $this->_itemInterpreter->expects($this->any())
+            ->method('evaluate')
+            ->will($this->returnCallback(function ($input) {
+                return '-' . $input['value'] . '-';
+            }));
+        $actual = $this->_model->evaluate($input);
+        $this->assertSame($expected, $actual);
     }
 
-    public function testEvaluate()
+    public function evaluateDataProvider()
     {
-        $this->_interpreter->expects($this->any())->method('evaluate')->will(
-            $this->returnCallback(
-                function ($input) {
-                    return '-' . $input['value'] . '-';
-                }
-            )
+        return array(
+            'empty array items' => array(
+                array('item' => array()),
+                array(),
+            ),
+            'absent array items' => array(
+                array(),
+                array(),
+            ),
+            'present array items' => array(
+                array(
+                    'item' => array(
+                        'key1' => array('value' => 'value 1'),
+                        'key2' => array('value' => 'value 2'),
+                        'key3' => array('value' => 'value 3'),
+                    ),
+                ),
+                array(
+                    'key1' => '-value 1-',
+                    'key2' => '-value 2-',
+                    'key3' => '-value 3-',
+                ),
+            ),
         );
-        $input = array(array('value' => 'value 1'), array('value' => 'value 2'), array('value' => 'value 3'));
-        $expected = array('-value 1-', '-value 2-', '-value 3-');
-        $actual = $this->_model->evaluate(array('item' => $input));
-        $this->assertSame($expected, $actual);
     }
 }
diff --git a/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/_files/typesInvalidArray.php b/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/_files/typesInvalidArray.php
index ad0cbbcca76..a9f92f2fd14 100644
--- a/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/_files/typesInvalidArray.php
+++ b/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/_files/typesInvalidArray.php
@@ -77,11 +77,6 @@ return array(
         <argument name="a" xsi:type="string"><child>v</child></argument></arguments>',
         array("Element 'child': This element is not expected.")
     ),
-    'array without items' => array(
-        '<?xml version="1.0"?><arguments xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
-        <argument name="a" xsi:type="array">v</argument></arguments>',
-        array("Element 'argument': Missing child element(s). Expected is ( item ).")
-    ),
     'array with forbidden child' => array(
         '<?xml version="1.0"?><arguments xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
         <argument name="a" xsi:type="array"><child>v</child></argument></arguments>',
diff --git a/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/_files/types_valid.xml b/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/_files/types_valid.xml
index 287c0997a49..6072f07aaed 100644
--- a/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/_files/types_valid.xml
+++ b/dev/tests/unit/testsuite/Magento/Framework/Data/Argument/_files/types_valid.xml
@@ -36,6 +36,7 @@
     <argument name="number" xsi:type="number">100500</argument>
     <argument name="object" xsi:type="object">Object</argument>
     <argument name="null Different symbols 1~!@#$%^&amp;*()_+-=`[]\{}|;':,./&lt;&gt;?" xsi:type="null" />
+    <argument name="empty_array" xsi:type="array"/>
     <argument name="single_array" xsi:type="array">
         <item name="key1 unique for single array" xsi:type="string">value</item>
         <item name="Different symbols 1~!@#$%^&amp;*()_+-=`[]\{}|;':,./&lt;&gt;?" xsi:type="string">2</item>
diff --git a/dev/tests/unit/testsuite/Magento/Install/Model/Installer/ConsoleTest.php b/dev/tests/unit/testsuite/Magento/Install/Model/Installer/ConsoleTest.php
index 9a5c446a025..fb13b45e3d5 100644
--- a/dev/tests/unit/testsuite/Magento/Install/Model/Installer/ConsoleTest.php
+++ b/dev/tests/unit/testsuite/Magento/Install/Model/Installer/ConsoleTest.php
@@ -25,21 +25,121 @@ namespace Magento\Install\Model\Installer;
 
 class ConsoleTest extends \PHPUnit_Framework_TestCase
 {
-
     /**
      * @var \Magento\Install\Model\Installer\Console
      */
     protected $model;
+
     /**
      * @var \Magento\Framework\App\Filesystem|\PHPUnit_Framework_MockObject_MockObject
      */
     protected $filesystemMock;
+
     /**
      * @var \Magento\Framework\Filesystem\Directory\Write|\PHPUnit_Framework_MockObject_MockObject
      */
     protected $directoryMock;
 
+    protected $defaultRenderer;
+
     protected function setUp()
+    {
+        $this->defaultRenderer = \Magento\Framework\Phrase::getRenderer();
+    }
+
+    /**
+     * {inheritdoc}
+     */
+    protected function tearDown()
+    {
+        $this->model = null;
+        \Magento\Framework\Phrase::setRenderer($this->defaultRenderer);
+    }
+
+    /**
+     * Test uninstall()
+     */
+    public function testUninstall()
+    {
+        $this->model = $this->getModelMock();
+
+        $this->directoryMock->expects($this->exactly(2))
+            ->method('delete')->with($this->logicalOr($this->equalTo(TESTS_TEMP_DIR), $this->equalTo('local.xml')))
+            ->will($this->returnValue(true));
+
+        $this->assertTrue($this->model->uninstall());
+
+    }
+
+    /**
+     * Test uninstall() when error is triggered
+     */
+    public function testUninstallWithError()
+    {
+        $this->model = $this->getModelMock();
+
+        $this->directoryMock->expects($this->exactly(2))
+            ->method('delete')->with($this->logicalOr($this->equalTo(TESTS_TEMP_DIR), $this->equalTo('local.xml')))
+            ->will(
+                $this->throwException(
+                    new \Magento\Framework\Filesystem\FilesystemException(sprintf(
+                        'The file "%s" cannot be deleted %s',
+                        TESTS_TEMP_DIR,
+                        "Warning"
+                    ))
+                )
+            );
+        $expectedString = str_repeat(sprintf('Please delete the file manually : "%s" ' . "\n", TESTS_TEMP_DIR), 2);
+
+        $this->filesystemMock->expects($this->any())->method('getDirectoryWrite')->will(
+            $this->returnValue($this->directoryMock)
+        );
+        $this->expectOutputString($expectedString);
+        $result = $this->model->uninstall();
+
+        $this->assertTrue($result);
+
+    }
+
+    /**
+     * @param array $items
+     * @param array $expectedResult
+     * @dataProvider checkServerDataProvider
+     */
+    public function testCheckServer($items, $expectedResult)
+    {
+        // 1. Create mocks
+        /** @var \Magento\Install\Model\Installer\Data|\PHPUnit_Framework_MockObject_MockObject $installerData */
+        list($this->model, $installerData) = $this->getMocks($items);
+
+        // 2. Set expectations
+        for ($i = 0; $i < count($items); $i++) {
+            $text = $expectedResult[$i];
+            $installerData->expects($this->at($i))->method('addError')->with($text);
+        }
+
+        // 3. Run tested method
+        $this->model->checkServer();
+    }
+
+    /**
+     * @return array
+     */
+    public function checkServerDataProvider()
+    {
+        $messageA = $this->getMockBuilder('SomeClass')->setMethods(['toString'])->getMock();
+        $messageA->expects($this->any())->method('toString')->will($this->returnValue('textA'));
+
+        $messageB = $this->getMockBuilder('SomeClass')->setMethods(['toString'])->getMock();
+        $messageB->expects($this->any())->method('toString')->will($this->returnValue('textB'));
+
+        return [
+            [[$messageA, $messageB], ['textA', 'textB']],
+            [[$messageB, $messageA], ['textB', 'textA']],
+        ];
+    }
+
+    protected function getModelMock()
     {
         $dbModelName = 'Magento\Install\Model\Installer\Db\Mysql4';
         $this->directoryMock = $this->getMock('Magento\Framework\Filesystem\Directory\Write', [], [], '', false);
@@ -71,7 +171,7 @@ class ConsoleTest extends \PHPUnit_Framework_TestCase
             $this->returnValue($dbModelMock)
         );
 
-        $this->model = new \Magento\Install\Model\Installer\Console(
+        return new \Magento\Install\Model\Installer\Console(
             $this->getMock('Magento\Install\Model\Installer', [], [], '', false),
             $this->getMock('Magento\Framework\App\Resource\Config', [], [], '', false),
             $this->getMock('Magento\Framework\Module\UpdaterInterface', [], [], '', false),
@@ -81,45 +181,49 @@ class ConsoleTest extends \PHPUnit_Framework_TestCase
             $this->getMock('Magento\Framework\Locale\ListsInterface', [], [], '', false),
             $objectManagerMock
         );
-
     }
 
-    protected function tearDown()
-    {
-        $this->model = null;
-    }
-
-
-    public function testUninstall()
-    {
-        $this->directoryMock->expects($this->exactly(2))
-            ->method('delete')->with($this->logicalOr($this->equalTo(TESTS_TEMP_DIR), $this->equalTo('local.xml')))
-            ->will($this->returnValue(true));
-
-        $this->assertTrue($this->model->uninstall());
-
-    }
-
-    public function testUninstallWithError()
+    /**
+     * @param array $items
+     * @return array
+     */
+    protected function getMocks($items)
     {
-        $this->directoryMock->expects($this->exactly(2))
-            ->method('delete')->with($this->logicalOr($this->equalTo(TESTS_TEMP_DIR), $this->equalTo('local.xml')))
-            ->will(
-                $this->throwException(
-                    new \Magento\Framework\Filesystem\FilesystemException(sprintf(
-                        'The file "%s" cannot be deleted %s',
-                        TESTS_TEMP_DIR,
-                        "Warning"
-                    ))
-                )
-            );
-        $expectedString = str_repeat(sprintf('Please delete the file manually : "%s" ' . "\n", TESTS_TEMP_DIR), 2);
-
-        $this->filesystemMock->expects($this->any())->method('getDirectoryWrite')->with()->will(
-            $this->returnValue($this->directoryMock)
-        );
-        $this->expectOutputString($expectedString);
-        $this->model->uninstall();
-
+        $helper = new \Magento\TestFramework\Helper\ObjectManager($this);
+
+        $installerData = $this->getMockBuilder('Magento\Install\Model\Installer\Data')
+            ->disableOriginalConstructor()
+            ->setMethods(['addError'])
+            ->getMock();
+
+        $phraseRenderer = $this->getMockBuilder('Magento\Framework\Phrase\RendererInterface')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $messageCollection = $this->getMockBuilder('SomeClass')
+            ->setMethods(['getItems'])
+            ->getMock();
+
+        $messageManager = $this->getMockBuilder('Magento\Framework\Message\ManagerInterface')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $objectManager = $this->getMockBuilder('Magento\Framework\ObjectManager')
+            ->disableOriginalConstructor()
+            ->getMock();
+
+        $messageCollection->expects($this->any())->method('getItems')->will($this->returnValue($items));
+        $messageManager->expects($this->any())->method('getMessages')->will($this->returnValue($messageCollection));
+        $objectManager->expects($this->any())->method('get')->will($this->returnValueMap([
+            ['Magento\Framework\Phrase\RendererInterface', $phraseRenderer],
+            ['Magento\Framework\Message\ManagerInterface', $messageManager],
+        ]));
+
+        $consoleInstaller = $helper->getObject('Magento\Install\Model\Installer\Console', [
+            'objectManager' => $objectManager,
+            'installerData' => $installerData,
+        ]);
+
+        return [$consoleInstaller, $installerData];
     }
 }
diff --git a/dev/tests/unit/testsuite/Magento/Sales/Model/OrderTest.php b/dev/tests/unit/testsuite/Magento/Sales/Model/OrderTest.php
index 7a010a4d08f..ff951321b56 100644
--- a/dev/tests/unit/testsuite/Magento/Sales/Model/OrderTest.php
+++ b/dev/tests/unit/testsuite/Magento/Sales/Model/OrderTest.php
@@ -96,7 +96,11 @@ class OrderTest extends \PHPUnit_Framework_TestCase
         $order->setData('state', $orderState);
         $this->_prepareOrderPayment(
             $order,
-            array('canReviewPayment' => $canReviewPayment, 'canFetchTransactionInfo' => $canUpdatePayment)
+            [
+                'canReviewPayment' => $canReviewPayment,
+                'canFetchTransactionInfo' => $canUpdatePayment,
+                'canVoid' => true
+            ]
         );
         $this->_prepareOrderItems($order, $allInvoiced);
 
@@ -133,6 +137,12 @@ class OrderTest extends \PHPUnit_Framework_TestCase
             $expectedResult = false;
         }
 
+        if (isset($actionFlags[\Magento\Sales\Model\Order::ACTION_FLAG_UNHOLD])
+        && $actionFlags[\Magento\Sales\Model\Order::ACTION_FLAG_UNHOLD] == false
+        && $orderState == \Magento\Sales\Model\Order::STATE_PAYMENT_REVIEW) {
+            $expectedResult = false;
+        }
+
         $this->assertEquals($expectedResult, $order->canCancel());
     }
 
diff --git a/lib/internal/Magento/Framework/App/Config.php b/lib/internal/Magento/Framework/App/Config.php
index 7b5a6f166fa..dc9e81550b0 100644
--- a/lib/internal/Magento/Framework/App/Config.php
+++ b/lib/internal/Magento/Framework/App/Config.php
@@ -71,6 +71,6 @@ class Config implements \Magento\Framework\App\Config\ScopeConfigInterface
      */
     public function isSetFlag($path, $scope = \Magento\Framework\App\ScopeInterface::SCOPE_DEFAULT, $scopeCode = null)
     {
-        return (bool)$this->getValue($path, $scope, $scopeCode);
+        return (bool) $this->getValue($path, $scope, $scopeCode);
     }
 }
diff --git a/lib/internal/Magento/Framework/App/EntryPoint/EntryPoint.php b/lib/internal/Magento/Framework/App/EntryPoint/EntryPoint.php
index 11571672baa..ebc7082fe4c 100644
--- a/lib/internal/Magento/Framework/App/EntryPoint/EntryPoint.php
+++ b/lib/internal/Magento/Framework/App/EntryPoint/EntryPoint.php
@@ -82,8 +82,8 @@ class EntryPoint implements EntryPointInterface
             $response->sendResponse();
         } catch (\Exception $exception) {
             if (isset(
-                $this->_parameters[state::PARAM_MODE]
-            ) && $this->_parameters[State::PARAM_MODE] == State::MODE_DEVELOPER
+                $this->_parameters[State::PARAM_MODE]
+                ) && $this->_parameters[State::PARAM_MODE] == State::MODE_DEVELOPER
             ) {
                 echo $exception->getMessage() . "\n\n";
                 echo $exception->getTraceAsString();
diff --git a/lib/internal/Magento/Framework/AppInterface.php b/lib/internal/Magento/Framework/AppInterface.php
index 12909ce6089..3800dabc2ff 100644
--- a/lib/internal/Magento/Framework/AppInterface.php
+++ b/lib/internal/Magento/Framework/AppInterface.php
@@ -35,7 +35,7 @@ interface AppInterface
     /**
      * Magento version
      */
-    const VERSION = '2.0.0.0-dev81';
+    const VERSION = '2.0.0.0-dev82';
 
     /**
      * Launch application
diff --git a/lib/internal/Magento/Framework/DB/Adapter/Pdo/Mysql.php b/lib/internal/Magento/Framework/DB/Adapter/Pdo/Mysql.php
index 49385b44bfb..82a19b402eb 100644
--- a/lib/internal/Magento/Framework/DB/Adapter/Pdo/Mysql.php
+++ b/lib/internal/Magento/Framework/DB/Adapter/Pdo/Mysql.php
@@ -1100,7 +1100,7 @@ class Mysql extends \Zend_Db_Adapter_Pdo_Mysql implements AdapterInterface
         $cacheKey = $this->_getTableName($tableName, $schemaName);
         $ddl = $this->loadDdlCache($cacheKey, self::DDL_CREATE);
         if ($ddl === false) {
-            $sql = 'SHOW CREATE TABLE ' . $this->quoteIdentifier($tableName);
+            $sql = 'SHOW CREATE TABLE ' . $this->quoteIdentifier($this->_getTableName($tableName, $schemaName));
             $ddl = $this->rawFetchRow($sql, 'Create Table');
             $this->saveDdlCache($cacheKey, self::DDL_CREATE, $ddl);
         }
diff --git a/lib/internal/Magento/Framework/DB/Helper/AbstractHelper.php b/lib/internal/Magento/Framework/DB/Helper/AbstractHelper.php
index b79e7fd3b67..88d3666faef 100644
--- a/lib/internal/Magento/Framework/DB/Helper/AbstractHelper.php
+++ b/lib/internal/Magento/Framework/DB/Helper/AbstractHelper.php
@@ -189,134 +189,4 @@ abstract class AbstractHelper
         $quotedField = $this->_getReadAdapter()->quoteIdentifier($field);
         return new \Zend_Db_Expr($quotedField . ' LIKE ' . $this->addLikeEscape($value, $options));
     }
-
-    /**
-     * Converts old pre-MMDB column definition for MySQL to new cross-db column DDL definition.
-     * Used to convert data from 3rd party extensions that hasn't been updated to MMDB style yet.
-     *
-     * E.g. Converts type 'varchar(255)' to array('type' => \Magento\Framework\DB\Ddl\Table::TYPE_TEXT, 'length' => 255)
-     *
-     * @param array $column
-     * @return array
-     * @throws \Magento\Framework\Model\Exception
-     */
-    public function convertOldColumnDefinition($column)
-    {
-        // Match type and size - e.g. varchar(100) or decimal(12,4) or int
-        $matches = array();
-        $definition = trim($column['type']);
-        if (!preg_match('/([^(]*)(\\((.*)\\))?/', $definition, $matches)) {
-            throw new \Magento\Framework\Model\Exception(__("Wrong old style column type definition: {$definition}."));
-        }
-
-        $length = null;
-        $proposedLength = isset($matches[3]) && strlen($matches[3]) ? $matches[3] : null;
-        switch (strtolower($matches[1])) {
-            case 'bool':
-                $length = null;
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_BOOLEAN;
-                break;
-            case 'char':
-            case 'varchar':
-            case 'tinytext':
-                $length = $proposedLength;
-                if (!$length) {
-                    $length = 255;
-                }
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_TEXT;
-                break;
-            case 'text':
-                $length = $proposedLength;
-                if (!$length) {
-                    $length = '64k';
-                }
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_TEXT;
-                break;
-            case 'mediumtext':
-                $length = $proposedLength;
-                if (!$length) {
-                    $length = '16M';
-                }
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_TEXT;
-                break;
-            case 'longtext':
-                $length = $proposedLength;
-                if (!$length) {
-                    $length = '4G';
-                }
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_TEXT;
-                break;
-            case 'blob':
-                $length = $proposedLength;
-                if (!$length) {
-                    $length = '64k';
-                }
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_BLOB;
-                break;
-            case 'mediumblob':
-                $length = $proposedLength;
-                if (!$length) {
-                    $length = '16M';
-                }
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_BLOB;
-                break;
-            case 'longblob':
-                $length = $proposedLength;
-                if (!$length) {
-                    $length = '4G';
-                }
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_BLOB;
-                break;
-            case 'tinyint':
-            case 'smallint':
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_SMALLINT;
-                break;
-            case 'mediumint':
-            case 'int':
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER;
-                break;
-            case 'bigint':
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_BIGINT;
-                break;
-            case 'float':
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_FLOAT;
-                break;
-            case 'decimal':
-            case 'numeric':
-                $length = $proposedLength;
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_DECIMAL;
-                break;
-            case 'datetime':
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_DATETIME;
-                break;
-            case 'timestamp':
-            case 'time':
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_TIMESTAMP;
-                break;
-            case 'date':
-                $type = \Magento\Framework\DB\Ddl\Table::TYPE_DATE;
-                break;
-            default:
-                throw new \Magento\Framework\Model\Exception(__("Unknown old style column type definition: {$definition}."));
-        }
-
-        $result = array(
-            'type' => $type,
-            'length' => $length,
-            'unsigned' => $column['unsigned'],
-            'nullable' => $column['is_null'],
-            'default' => $column['default'],
-            'identity' => stripos($column['extra'], 'auto_increment') !== false
-        );
-
-        /**
-         * Process the case when 'is_null' prohibits null value, and 'default' proposed to be null.
-         * It just means that default value not specified, and we must remove it from column definition.
-         */
-        if (false === $column['is_null'] && null === $column['default']) {
-            unset($result['default']);
-        }
-
-        return $result;
-    }
 }
diff --git a/lib/internal/Magento/Framework/Data/Argument/Interpreter/ArrayType.php b/lib/internal/Magento/Framework/Data/Argument/Interpreter/ArrayType.php
index ca0e0e67c57..c250ade73d9 100644
--- a/lib/internal/Magento/Framework/Data/Argument/Interpreter/ArrayType.php
+++ b/lib/internal/Magento/Framework/Data/Argument/Interpreter/ArrayType.php
@@ -52,11 +52,11 @@ class ArrayType implements InterpreterInterface
      */
     public function evaluate(array $data)
     {
-        if (!isset($data['item']) || !is_array($data['item'])) {
+        $items = isset($data['item']) ? $data['item'] : array();
+        if (!is_array($items)) {
             throw new \InvalidArgumentException('Array items are expected.');
         }
         $result = array();
-        $items = $data['item'];
         foreach ($items as $itemKey => $itemData) {
             $result[$itemKey] = $this->itemInterpreter->evaluate($itemData);
         }
diff --git a/lib/internal/Magento/Framework/Data/etc/argument/types.xsd b/lib/internal/Magento/Framework/Data/etc/argument/types.xsd
index 6d21a1c407a..ecf2ffdc295 100644
--- a/lib/internal/Magento/Framework/Data/etc/argument/types.xsd
+++ b/lib/internal/Magento/Framework/Data/etc/argument/types.xsd
@@ -33,7 +33,7 @@
         <xs:complexContent>
             <xs:extension base="argumentType">
                 <xs:sequence>
-                    <xs:element name="item" type="argumentType" minOccurs="1" maxOccurs="unbounded">
+                    <xs:element name="item" type="argumentType" minOccurs="0" maxOccurs="unbounded">
                         <xs:key name="itemName">
                             <xs:selector xpath="item"></xs:selector>
                             <xs:field xpath="@name"></xs:field>
diff --git a/lib/web/jquery/jquery-ui-timepicker-addon-1.0.1.js b/lib/web/jquery/jquery-ui-timepicker-addon-1.0.1.js
deleted file mode 100644
index 8d5a1072060..00000000000
--- a/lib/web/jquery/jquery-ui-timepicker-addon-1.0.1.js
+++ /dev/null
@@ -1,1530 +0,0 @@
-/*
-* jQuery timepicker addon
-* By: Trent Richardson [http://trentrichardson.com]
-* Version 1.0.1
-* Last Modified: 07/01/2012
-*
-* Copyright 2012 Trent Richardson
-* You may use this project under MIT or GPL licenses.
-* http://trentrichardson.com/Impromptu/GPL-LICENSE.txt
-* http://trentrichardson.com/Impromptu/MIT-LICENSE.txt
-*
-* HERES THE CSS:
-* .ui-timepicker-div .ui-widget-header { margin-bottom: 8px; }
-* .ui-timepicker-div dl { text-align: left; }
-* .ui-timepicker-div dl dt { height: 25px; margin-bottom: -25px; }
-* .ui-timepicker-div dl dd { margin: 0 10px 10px 65px; }
-* .ui-timepicker-div td { font-size: 90%; }
-* .ui-tpicker-grid-label { background: none; border: none; margin: 0; padding: 0; }
-*/
-
-/*jslint evil: true, maxlen: 300, white: false, undef: false, nomen: false, onevar: false */
-
-(function($) {
-
-// Prevent "Uncaught RangeError: Maximum call stack size exceeded"
-$.ui.timepicker = $.ui.timepicker || {};
-if ($.ui.timepicker.version) {
-	return;
-}
-
-$.extend($.ui, { timepicker: { version: "1.0.1" } });
-
-/* Time picker manager.
-   Use the singleton instance of this class, $.timepicker, to interact with the time picker.
-   Settings for (groups of) time pickers are maintained in an instance object,
-   allowing multiple different settings on the same page. */
-
-function Timepicker() {
-	this.regional = []; // Available regional settings, indexed by language code
-	this.regional[''] = { // Default regional settings
-		currentText: 'Now',
-		closeText: 'Done',
-		ampm: false,
-		amNames: ['AM', 'A'],
-		pmNames: ['PM', 'P'],
-		timeFormat: 'hh:mm tt',
-		timeSuffix: '',
-		timeOnlyTitle: 'Choose Time',
-		timeText: 'Time',
-		hourText: 'Hour',
-		minuteText: 'Minute',
-		secondText: 'Second',
-		millisecText: 'Millisecond',
-		timezoneText: 'Time Zone'
-	};
-	this._defaults = { // Global defaults for all the datetime picker instances
-		showButtonPanel: true,
-		timeOnly: false,
-		showHour: true,
-		showMinute: true,
-		showSecond: false,
-		showMillisec: false,
-		showTimezone: false,
-		showTime: true,
-		stepHour: 1,
-		stepMinute: 1,
-		stepSecond: 1,
-		stepMillisec: 1,
-		hour: 0,
-		minute: 0,
-		second: 0,
-		millisec: 0,
-		timezone: null,
-		useLocalTimezone: false,
-		defaultTimezone: "+0000",
-		hourMin: 0,
-		minuteMin: 0,
-		secondMin: 0,
-		millisecMin: 0,
-		hourMax: 23,
-		minuteMax: 59,
-		secondMax: 59,
-		millisecMax: 999,
-		minDateTime: null,
-		maxDateTime: null,
-		onSelect: null,
-		hourGrid: 0,
-		minuteGrid: 0,
-		secondGrid: 0,
-		millisecGrid: 0,
-		alwaysSetTime: true,
-		separator: ' ',
-		altFieldTimeOnly: true,
-		showTimepicker: true,
-		timezoneIso8601: false,
-		timezoneList: null,
-		addSliderAccess: false,
-		sliderAccessArgs: null
-	};
-	$.extend(this._defaults, this.regional['']);
-}
-
-$.extend(Timepicker.prototype, {
-	$input: null,
-	$altInput: null,
-	$timeObj: null,
-	inst: null,
-	hour_slider: null,
-	minute_slider: null,
-	second_slider: null,
-	millisec_slider: null,
-	timezone_select: null,
-	hour: 0,
-	minute: 0,
-	second: 0,
-	millisec: 0,
-	timezone: null,
-	defaultTimezone: "+0000",
-	hourMinOriginal: null,
-	minuteMinOriginal: null,
-	secondMinOriginal: null,
-	millisecMinOriginal: null,
-	hourMaxOriginal: null,
-	minuteMaxOriginal: null,
-	secondMaxOriginal: null,
-	millisecMaxOriginal: null,
-	ampm: '',
-	formattedDate: '',
-	formattedTime: '',
-	formattedDateTime: '',
-	timezoneList: null,
-
-	/* Override the default settings for all instances of the time picker.
-	   @param  settings  object - the new settings to use as defaults (anonymous object)
-	   @return the manager object */
-	setDefaults: function(settings) {
-		extendRemove(this._defaults, settings || {});
-		return this;
-	},
-
-	//########################################################################
-	// Create a new Timepicker instance
-	//########################################################################
-	_newInst: function($input, o) {
-		var tp_inst = new Timepicker(),
-			inlineSettings = {};
-
-		for (var attrName in this._defaults) {
-			var attrValue = $input.attr('time:' + attrName);
-			if (attrValue) {
-				try {
-					inlineSettings[attrName] = eval(attrValue);
-				} catch (err) {
-					inlineSettings[attrName] = attrValue;
-				}
-			}
-		}
-		tp_inst._defaults = $.extend({}, this._defaults, inlineSettings, o, {
-			beforeShow: function(input, dp_inst) {
-				if ($.isFunction(o.beforeShow)) {
-					return o.beforeShow(input, dp_inst, tp_inst);
-                }
-			},
-			onChangeMonthYear: function(year, month, dp_inst) {
-				// Update the time as well : this prevents the time from disappearing from the $input field.
-				tp_inst._updateDateTime(dp_inst);
-				if ($.isFunction(o.onChangeMonthYear)) {
-					o.onChangeMonthYear.call($input[0], year, month, dp_inst, tp_inst);
-                }
-			},
-			onClose: function(dateText, dp_inst) {
-				if (tp_inst.timeDefined === true && $input.val() !== '') {
-					tp_inst._updateDateTime(dp_inst);
-                }
-				if ($.isFunction(o.onClose)) {
-					o.onClose.call($input[0], dateText, dp_inst, tp_inst);
-                }
-			},
-			timepicker: tp_inst // add timepicker as a property of datepicker: $.datepicker._get(dp_inst, 'timepicker');
-		});
-		tp_inst.amNames = $.map(tp_inst._defaults.amNames, function(val) { return val.toUpperCase(); });
-		tp_inst.pmNames = $.map(tp_inst._defaults.pmNames, function(val) { return val.toUpperCase(); });
-
-		if (tp_inst._defaults.timezoneList === null) {
-			var timezoneList = [];
-			for (var i = -11; i <= 12; i++) {
-				timezoneList.push((i >= 0 ? '+' : '-') + ('0' + Math.abs(i).toString()).slice(-2) + '00');
-            }
-			if (tp_inst._defaults.timezoneIso8601) {
-				timezoneList = $.map(timezoneList, function(val) {
-					return val == '+0000' ? 'Z' : (val.substring(0, 3) + ':' + val.substring(3));
-				});
-            }
-			tp_inst._defaults.timezoneList = timezoneList;
-		}
-
-		tp_inst.timezone = tp_inst._defaults.timezone;
-		tp_inst.hour = tp_inst._defaults.hour;
-		tp_inst.minute = tp_inst._defaults.minute;
-		tp_inst.second = tp_inst._defaults.second;
-		tp_inst.millisec = tp_inst._defaults.millisec;
-		tp_inst.ampm = '';
-		tp_inst.$input = $input;
-
-		if (o.altField) {
-			tp_inst.$altInput = $(o.altField)
-				.css({ cursor: 'pointer' })
-				.focus(function(){ $input.trigger("focus"); });
-        }
-
-		if(tp_inst._defaults.minDate===0 || tp_inst._defaults.minDateTime===0)
-		{
-			tp_inst._defaults.minDate=new Date();
-		}
-		if(tp_inst._defaults.maxDate===0 || tp_inst._defaults.maxDateTime===0)
-		{
-			tp_inst._defaults.maxDate=new Date();
-		}
-
-		// datepicker needs minDate/maxDate, timepicker needs minDateTime/maxDateTime..
-		if(tp_inst._defaults.minDate !== undefined && tp_inst._defaults.minDate instanceof Date) {
-			tp_inst._defaults.minDateTime = new Date(tp_inst._defaults.minDate.getTime());
-        }
-		if(tp_inst._defaults.minDateTime !== undefined && tp_inst._defaults.minDateTime instanceof Date) {
-			tp_inst._defaults.minDate = new Date(tp_inst._defaults.minDateTime.getTime());
-        }
-		if(tp_inst._defaults.maxDate !== undefined && tp_inst._defaults.maxDate instanceof Date) {
-			tp_inst._defaults.maxDateTime = new Date(tp_inst._defaults.maxDate.getTime());
-        }
-		if(tp_inst._defaults.maxDateTime !== undefined && tp_inst._defaults.maxDateTime instanceof Date) {
-			tp_inst._defaults.maxDate = new Date(tp_inst._defaults.maxDateTime.getTime());
-        }
-		return tp_inst;
-	},
-
-	//########################################################################
-	// add our sliders to the calendar
-	//########################################################################
-	_addTimePicker: function(dp_inst) {
-		var currDT = (this.$altInput && this._defaults.altFieldTimeOnly) ?
-				this.$input.val() + ' ' + this.$altInput.val() :
-				this.$input.val();
-
-		this.timeDefined = this._parseTime(currDT);
-		this._limitMinMaxDateTime(dp_inst, false);
-		this._injectTimePicker();
-	},
-
-	//########################################################################
-	// parse the time string from input value or _setTime
-	//########################################################################
-	_parseTime: function(timeString, withDate) {
-		if (!this.inst) {
-			this.inst = $.datepicker._getInst(this.$input[0]);
-		}
-		
-		if (withDate || !this._defaults.timeOnly) 
-		{
-			var dp_dateFormat = $.datepicker._get(this.inst, 'dateFormat');
-			try {
-				var parseRes = parseDateTimeInternal(dp_dateFormat, this._defaults.timeFormat, timeString, $.datepicker._getFormatConfig(this.inst), this._defaults);
-				if (!parseRes.timeObj) { return false; }
-				$.extend(this, parseRes.timeObj);
-			} catch (err)
-			{
-				return false;
-			}
-			return true;
-		}
-		else
-		{
-			var timeObj = $.datepicker.parseTime(this._defaults.timeFormat, timeString, this._defaults);
-			if(!timeObj) { return false; }
-			$.extend(this, timeObj);
-			return true;
-		}
-	},
-	
-	//########################################################################
-	// generate and inject html for timepicker into ui datepicker
-	//########################################################################
-	_injectTimePicker: function() {
-		var $dp = this.inst.dpDiv,
-			o = this._defaults,
-			tp_inst = this,
-			// Added by Peter Medeiros:
-			// - Figure out what the hour/minute/second max should be based on the step values.
-			// - Example: if stepMinute is 15, then minMax is 45.
-			hourMax = parseInt((o.hourMax - ((o.hourMax - o.hourMin) % o.stepHour)) ,10),
-			minMax  = parseInt((o.minuteMax - ((o.minuteMax - o.minuteMin) % o.stepMinute)) ,10),
-			secMax  = parseInt((o.secondMax - ((o.secondMax - o.secondMin) % o.stepSecond)) ,10),
-			millisecMax  = parseInt((o.millisecMax - ((o.millisecMax - o.millisecMin) % o.stepMillisec)) ,10),
-			dp_id = this.inst.id.toString().replace(/([^A-Za-z0-9_])/g, '');
-
-		// Prevent displaying twice
-		//if ($dp.find("div#ui-timepicker-div-"+ dp_id).length === 0) {
-		if ($dp.find("div#ui-timepicker-div-"+ dp_id).length === 0 && o.showTimepicker) {
-			var noDisplay = ' style="display:none;"',
-				html =	'<div class="ui-timepicker-div" id="ui-timepicker-div-' + dp_id + '"><dl>' +
-						'<dt class="ui_tpicker_time_label" id="ui_tpicker_time_label_' + dp_id + '"' +
-						((o.showTime) ? '' : noDisplay) + '>' + o.timeText + '</dt>' +
-						'<dd class="ui_tpicker_time" id="ui_tpicker_time_' + dp_id + '"' +
-						((o.showTime) ? '' : noDisplay) + '></dd>' +
-						'<dt class="ui_tpicker_hour_label" id="ui_tpicker_hour_label_' + dp_id + '"' +
-						((o.showHour) ? '' : noDisplay) + '>' + o.hourText + '</dt>',
-				hourGridSize = 0,
-				minuteGridSize = 0,
-				secondGridSize = 0,
-				millisecGridSize = 0,
-				size = null;
-
-            // Hours
-			html += '<dd class="ui_tpicker_hour"><div id="ui_tpicker_hour_' + dp_id + '"' +
-						((o.showHour) ? '' : noDisplay) + '></div>';
-			if (o.showHour && o.hourGrid > 0) {
-				html += '<div style="padding-left: 1px"><table class="ui-tpicker-grid-label"><tr>';
-
-				for (var h = o.hourMin; h <= hourMax; h += parseInt(o.hourGrid,10)) {
-					hourGridSize++;
-					var tmph = (o.ampm && h > 12) ? h-12 : h;
-					if (tmph < 10) { tmph = '0' + tmph; }
-					if (o.ampm) {
-						if (h === 0) {
-                            tmph = 12 +'a';
-                        } else {
-                            if (h < 12) { tmph += 'a'; }
-						    else { tmph += 'p'; }
-                        }
-					}
-					html += '<td>' + tmph + '</td>';
-				}
-
-				html += '</tr></table></div>';
-			}
-			html += '</dd>';
-
-			// Minutes
-			html += '<dt class="ui_tpicker_minute_label" id="ui_tpicker_minute_label_' + dp_id + '"' +
-					((o.showMinute) ? '' : noDisplay) + '>' + o.minuteText + '</dt>'+
-					'<dd class="ui_tpicker_minute"><div id="ui_tpicker_minute_' + dp_id + '"' +
-							((o.showMinute) ? '' : noDisplay) + '></div>';
-
-			if (o.showMinute && o.minuteGrid > 0) {
-				html += '<div style="padding-left: 1px"><table class="ui-tpicker-grid-label"><tr>';
-
-				for (var m = o.minuteMin; m <= minMax; m += parseInt(o.minuteGrid,10)) {
-					minuteGridSize++;
-					html += '<td>' + ((m < 10) ? '0' : '') + m + '</td>';
-				}
-
-				html += '</tr></table></div>';
-			}
-			html += '</dd>';
-
-			// Seconds
-			html += '<dt class="ui_tpicker_second_label" id="ui_tpicker_second_label_' + dp_id + '"' +
-					((o.showSecond) ? '' : noDisplay) + '>' + o.secondText + '</dt>'+
-					'<dd class="ui_tpicker_second"><div id="ui_tpicker_second_' + dp_id + '"'+
-							((o.showSecond) ? '' : noDisplay) + '></div>';
-
-			if (o.showSecond && o.secondGrid > 0) {
-				html += '<div style="padding-left: 1px"><table><tr>';
-
-				for (var s = o.secondMin; s <= secMax; s += parseInt(o.secondGrid,10)) {
-					secondGridSize++;
-					html += '<td>' + ((s < 10) ? '0' : '') + s + '</td>';
-				}
-
-				html += '</tr></table></div>';
-			}
-			html += '</dd>';
-
-			// Milliseconds
-			html += '<dt class="ui_tpicker_millisec_label" id="ui_tpicker_millisec_label_' + dp_id + '"' +
-					((o.showMillisec) ? '' : noDisplay) + '>' + o.millisecText + '</dt>'+
-					'<dd class="ui_tpicker_millisec"><div id="ui_tpicker_millisec_' + dp_id + '"'+
-							((o.showMillisec) ? '' : noDisplay) + '></div>';
-
-			if (o.showMillisec && o.millisecGrid > 0) {
-				html += '<div style="padding-left: 1px"><table><tr>';
-
-				for (var l = o.millisecMin; l <= millisecMax; l += parseInt(o.millisecGrid,10)) {
-					millisecGridSize++;
-					html += '<td>' + ((l < 10) ? '0' : '') + l + '</td>';
-				}
-
-				html += '</tr></table></div>';
-			}
-			html += '</dd>';
-
-			// Timezone
-			html += '<dt class="ui_tpicker_timezone_label" id="ui_tpicker_timezone_label_' + dp_id + '"' +
-					((o.showTimezone) ? '' : noDisplay) + '>' + o.timezoneText + '</dt>';
-			html += '<dd class="ui_tpicker_timezone" id="ui_tpicker_timezone_' + dp_id + '"'	+
-							((o.showTimezone) ? '' : noDisplay) + '></dd>';
-
-			html += '</dl></div>';
-			var $tp = $(html);
-
-				// if we only want time picker...
-			if (o.timeOnly === true) {
-				$tp.prepend(
-					'<div class="ui-widget-header ui-helper-clearfix ui-corner-all">' +
-						'<div class="ui-datepicker-title">' + o.timeOnlyTitle + '</div>' +
-					'</div>');
-				$dp.find('.ui-datepicker-header, .ui-datepicker-calendar').hide();
-			}
-
-			this.hour_slider = $tp.find('#ui_tpicker_hour_'+ dp_id).slider({
-				orientation: "horizontal",
-				value: this.hour,
-				min: o.hourMin,
-				max: hourMax,
-				step: o.stepHour,
-				slide: function(event, ui) {
-					tp_inst.hour_slider.slider( "option", "value", ui.value);
-					tp_inst._onTimeChange();
-				}
-			});
-
-
-			// Updated by Peter Medeiros:
-			// - Pass in Event and UI instance into slide function
-			this.minute_slider = $tp.find('#ui_tpicker_minute_'+ dp_id).slider({
-				orientation: "horizontal",
-				value: this.minute,
-				min: o.minuteMin,
-				max: minMax,
-				step: o.stepMinute,
-				slide: function(event, ui) {
-					tp_inst.minute_slider.slider( "option", "value", ui.value);
-					tp_inst._onTimeChange();
-				}
-			});
-
-			this.second_slider = $tp.find('#ui_tpicker_second_'+ dp_id).slider({
-				orientation: "horizontal",
-				value: this.second,
-				min: o.secondMin,
-				max: secMax,
-				step: o.stepSecond,
-				slide: function(event, ui) {
-					tp_inst.second_slider.slider( "option", "value", ui.value);
-					tp_inst._onTimeChange();
-				}
-			});
-
-			this.millisec_slider = $tp.find('#ui_tpicker_millisec_'+ dp_id).slider({
-				orientation: "horizontal",
-				value: this.millisec,
-				min: o.millisecMin,
-				max: millisecMax,
-				step: o.stepMillisec,
-				slide: function(event, ui) {
-					tp_inst.millisec_slider.slider( "option", "value", ui.value);
-					tp_inst._onTimeChange();
-				}
-			});
-
-			this.timezone_select = $tp.find('#ui_tpicker_timezone_'+ dp_id).append('<select></select>').find("select");
-			$.fn.append.apply(this.timezone_select,
-				$.map(o.timezoneList, function(val, idx) {
-					return $("<option />")
-						.val(typeof val == "object" ? val.value : val)
-						.text(typeof val == "object" ? val.label : val);
-				})
-			);
-			if (typeof(this.timezone) != "undefined" && this.timezone !== null && this.timezone !== "") {
-				var local_date = new Date(this.inst.selectedYear, this.inst.selectedMonth, this.inst.selectedDay, 12);
-				var local_timezone = timeZoneString(local_date);
-				if (local_timezone == this.timezone) {
-					selectLocalTimeZone(tp_inst);
-				} else {
-					this.timezone_select.val(this.timezone);
-				}
-			} else {
-				if (typeof(this.hour) != "undefined" && this.hour !== null && this.hour !== "") {
-					this.timezone_select.val(o.defaultTimezone);
-				} else {
-					selectLocalTimeZone(tp_inst);
-				}
-			}
-			this.timezone_select.change(function() {
-				tp_inst._defaults.useLocalTimezone = false;
-				tp_inst._onTimeChange();
-			});
-
-			// Add grid functionality
-			if (o.showHour && o.hourGrid > 0) {
-				size = 100 * hourGridSize * o.hourGrid / (hourMax - o.hourMin);
-
-				$tp.find(".ui_tpicker_hour table").css({
-					width: size + "%",
-					marginLeft: (size / (-2 * hourGridSize)) + "%",
-					borderCollapse: 'collapse'
-				}).find("td").each( function(index) {
-					$(this).click(function() {
-						var h = $(this).html();
-						if(o.ampm)	{
-							var ap = h.substring(2).toLowerCase(),
-								aph = parseInt(h.substring(0,2), 10);
-							if (ap == 'a') {
-								if (aph == 12) { h = 0; }
-								else { h = aph; }
-							} else if (aph == 12) { h = 12; }
-							else { h = aph + 12; }
-						}
-						tp_inst.hour_slider.slider("option", "value", h);
-						tp_inst._onTimeChange();
-						tp_inst._onSelectHandler();
-					}).css({
-						cursor: 'pointer',
-						width: (100 / hourGridSize) + '%',
-						textAlign: 'center',
-						overflow: 'hidden'
-					});
-				});
-			}
-
-			if (o.showMinute && o.minuteGrid > 0) {
-				size = 100 * minuteGridSize * o.minuteGrid / (minMax - o.minuteMin);
-				$tp.find(".ui_tpicker_minute table").css({
-					width: size + "%",
-					marginLeft: (size / (-2 * minuteGridSize)) + "%",
-					borderCollapse: 'collapse'
-				}).find("td").each(function(index) {
-					$(this).click(function() {
-						tp_inst.minute_slider.slider("option", "value", $(this).html());
-						tp_inst._onTimeChange();
-						tp_inst._onSelectHandler();
-					}).css({
-						cursor: 'pointer',
-						width: (100 / minuteGridSize) + '%',
-						textAlign: 'center',
-						overflow: 'hidden'
-					});
-				});
-			}
-
-			if (o.showSecond && o.secondGrid > 0) {
-				$tp.find(".ui_tpicker_second table").css({
-					width: size + "%",
-					marginLeft: (size / (-2 * secondGridSize)) + "%",
-					borderCollapse: 'collapse'
-				}).find("td").each(function(index) {
-					$(this).click(function() {
-						tp_inst.second_slider.slider("option", "value", $(this).html());
-						tp_inst._onTimeChange();
-						tp_inst._onSelectHandler();
-					}).css({
-						cursor: 'pointer',
-						width: (100 / secondGridSize) + '%',
-						textAlign: 'center',
-						overflow: 'hidden'
-					});
-				});
-			}
-
-			if (o.showMillisec && o.millisecGrid > 0) {
-				$tp.find(".ui_tpicker_millisec table").css({
-					width: size + "%",
-					marginLeft: (size / (-2 * millisecGridSize)) + "%",
-					borderCollapse: 'collapse'
-				}).find("td").each(function(index) {
-					$(this).click(function() {
-						tp_inst.millisec_slider.slider("option", "value", $(this).html());
-						tp_inst._onTimeChange();
-						tp_inst._onSelectHandler();
-					}).css({
-						cursor: 'pointer',
-						width: (100 / millisecGridSize) + '%',
-						textAlign: 'center',
-						overflow: 'hidden'
-					});
-				});
-			}
-
-			var $buttonPanel = $dp.find('.ui-datepicker-buttonpane');
-			if ($buttonPanel.length) { $buttonPanel.before($tp); }
-			else { $dp.append($tp); }
-
-			this.$timeObj = $tp.find('#ui_tpicker_time_'+ dp_id);
-
-			if (this.inst !== null) {
-				var timeDefined = this.timeDefined;
-				this._onTimeChange();
-				this.timeDefined = timeDefined;
-			}
-
-			//Emulate datepicker onSelect behavior. Call on slidestop.
-			var onSelectDelegate = function() {
-				tp_inst._onSelectHandler();
-			};
-			this.hour_slider.bind('slidestop',onSelectDelegate);
-			this.minute_slider.bind('slidestop',onSelectDelegate);
-			this.second_slider.bind('slidestop',onSelectDelegate);
-			this.millisec_slider.bind('slidestop',onSelectDelegate);
-
-			// slideAccess integration: http://trentrichardson.com/2011/11/11/jquery-ui-sliders-and-touch-accessibility/
-			if (this._defaults.addSliderAccess){
-				var sliderAccessArgs = this._defaults.sliderAccessArgs;
-				setTimeout(function(){ // fix for inline mode
-					if($tp.find('.ui-slider-access').length === 0){
-						$tp.find('.ui-slider:visible').sliderAccess(sliderAccessArgs);
-
-						// fix any grids since sliders are shorter
-						var sliderAccessWidth = $tp.find('.ui-slider-access:eq(0)').outerWidth(true);
-						if(sliderAccessWidth){
-							$tp.find('table:visible').each(function(){
-								var $g = $(this),
-									oldWidth = $g.outerWidth(),
-									oldMarginLeft = $g.css('marginLeft').toString().replace('%',''),
-									newWidth = oldWidth - sliderAccessWidth,
-									newMarginLeft = ((oldMarginLeft * newWidth)/oldWidth) + '%';
-
-								$g.css({ width: newWidth, marginLeft: newMarginLeft });
-							});
-						}
-					}
-				},0);
-			}
-			// end slideAccess integration
-
-		}
-	},
-
-	//########################################################################
-	// This function tries to limit the ability to go outside the
-	// min/max date range
-	//########################################################################
-	_limitMinMaxDateTime: function(dp_inst, adjustSliders){
-		var o = this._defaults,
-			dp_date = new Date(dp_inst.selectedYear, dp_inst.selectedMonth, dp_inst.selectedDay);
-
-		if(!this._defaults.showTimepicker) { return; } // No time so nothing to check here
-
-		if($.datepicker._get(dp_inst, 'minDateTime') !== null && $.datepicker._get(dp_inst, 'minDateTime') !== undefined && dp_date){
-			var minDateTime = $.datepicker._get(dp_inst, 'minDateTime'),
-				minDateTimeDate = new Date(minDateTime.getFullYear(), minDateTime.getMonth(), minDateTime.getDate(), 0, 0, 0, 0);
-
-			if(this.hourMinOriginal === null || this.minuteMinOriginal === null || this.secondMinOriginal === null || this.millisecMinOriginal === null){
-				this.hourMinOriginal = o.hourMin;
-				this.minuteMinOriginal = o.minuteMin;
-				this.secondMinOriginal = o.secondMin;
-				this.millisecMinOriginal = o.millisecMin;
-			}
-
-			if(dp_inst.settings.timeOnly || minDateTimeDate.getTime() == dp_date.getTime()) {
-				this._defaults.hourMin = minDateTime.getHours();
-				if (this.hour <= this._defaults.hourMin) {
-					this.hour = this._defaults.hourMin;
-					this._defaults.minuteMin = minDateTime.getMinutes();
-					if (this.minute <= this._defaults.minuteMin) {
-						this.minute = this._defaults.minuteMin;
-						this._defaults.secondMin = minDateTime.getSeconds();
-					} else if (this.second <= this._defaults.secondMin){
-						this.second = this._defaults.secondMin;
-						this._defaults.millisecMin = minDateTime.getMilliseconds();
-					} else {
-						if(this.millisec < this._defaults.millisecMin) {
-							this.millisec = this._defaults.millisecMin;
-                        }
-						this._defaults.millisecMin = this.millisecMinOriginal;
-					}
-				} else {
-					this._defaults.minuteMin = this.minuteMinOriginal;
-					this._defaults.secondMin = this.secondMinOriginal;
-					this._defaults.millisecMin = this.millisecMinOriginal;
-				}
-			}else{
-				this._defaults.hourMin = this.hourMinOriginal;
-				this._defaults.minuteMin = this.minuteMinOriginal;
-				this._defaults.secondMin = this.secondMinOriginal;
-				this._defaults.millisecMin = this.millisecMinOriginal;
-			}
-		}
-
-		if($.datepicker._get(dp_inst, 'maxDateTime') !== null && $.datepicker._get(dp_inst, 'maxDateTime') !== undefined && dp_date){
-			var maxDateTime = $.datepicker._get(dp_inst, 'maxDateTime'),
-				maxDateTimeDate = new Date(maxDateTime.getFullYear(), maxDateTime.getMonth(), maxDateTime.getDate(), 0, 0, 0, 0);
-
-			if(this.hourMaxOriginal === null || this.minuteMaxOriginal === null || this.secondMaxOriginal === null){
-				this.hourMaxOriginal = o.hourMax;
-				this.minuteMaxOriginal = o.minuteMax;
-				this.secondMaxOriginal = o.secondMax;
-				this.millisecMaxOriginal = o.millisecMax;
-			}
-
-			if(dp_inst.settings.timeOnly || maxDateTimeDate.getTime() == dp_date.getTime()){
-				this._defaults.hourMax = maxDateTime.getHours();
-				if (this.hour >= this._defaults.hourMax) {
-					this.hour = this._defaults.hourMax;
-					this._defaults.minuteMax = maxDateTime.getMinutes();
-					if (this.minute >= this._defaults.minuteMax) {
-						this.minute = this._defaults.minuteMax;
-						this._defaults.secondMax = maxDateTime.getSeconds();
-					} else if (this.second >= this._defaults.secondMax) {
-						this.second = this._defaults.secondMax;
-						this._defaults.millisecMax = maxDateTime.getMilliseconds();
-					} else {
-						if(this.millisec > this._defaults.millisecMax) { this.millisec = this._defaults.millisecMax; }
-						this._defaults.millisecMax = this.millisecMaxOriginal;
-					}
-				} else {
-					this._defaults.minuteMax = this.minuteMaxOriginal;
-					this._defaults.secondMax = this.secondMaxOriginal;
-					this._defaults.millisecMax = this.millisecMaxOriginal;
-				}
-			}else{
-				this._defaults.hourMax = this.hourMaxOriginal;
-				this._defaults.minuteMax = this.minuteMaxOriginal;
-				this._defaults.secondMax = this.secondMaxOriginal;
-				this._defaults.millisecMax = this.millisecMaxOriginal;
-			}
-		}
-
-		if(adjustSliders !== undefined && adjustSliders === true){
-			var hourMax = parseInt((this._defaults.hourMax - ((this._defaults.hourMax - this._defaults.hourMin) % this._defaults.stepHour)) ,10),
-                minMax  = parseInt((this._defaults.minuteMax - ((this._defaults.minuteMax - this._defaults.minuteMin) % this._defaults.stepMinute)) ,10),
-                secMax  = parseInt((this._defaults.secondMax - ((this._defaults.secondMax - this._defaults.secondMin) % this._defaults.stepSecond)) ,10),
-				millisecMax  = parseInt((this._defaults.millisecMax - ((this._defaults.millisecMax - this._defaults.millisecMin) % this._defaults.stepMillisec)) ,10);
-
-			if(this.hour_slider) {
-				this.hour_slider.slider("option", { min: this._defaults.hourMin, max: hourMax }).slider('value', this.hour);
-            }
-			if(this.minute_slider) {
-				this.minute_slider.slider("option", { min: this._defaults.minuteMin, max: minMax }).slider('value', this.minute);
-            }
-			if(this.second_slider){
-				this.second_slider.slider("option", { min: this._defaults.secondMin, max: secMax }).slider('value', this.second);
-            }
-			if(this.millisec_slider) {
-				this.millisec_slider.slider("option", { min: this._defaults.millisecMin, max: millisecMax }).slider('value', this.millisec);
-            }
-		}
-
-	},
-
-
-	//########################################################################
-	// when a slider moves, set the internal time...
-	// on time change is also called when the time is updated in the text field
-	//########################################################################
-	_onTimeChange: function() {
-		var hour   = (this.hour_slider) ? this.hour_slider.slider('value') : false,
-			minute = (this.minute_slider) ? this.minute_slider.slider('value') : false,
-			second = (this.second_slider) ? this.second_slider.slider('value') : false,
-			millisec = (this.millisec_slider) ? this.millisec_slider.slider('value') : false,
-			timezone = (this.timezone_select) ? this.timezone_select.val() : false,
-			o = this._defaults;
-
-		if (typeof(hour) == 'object') { hour = false; }
-		if (typeof(minute) == 'object') { minute = false; }
-		if (typeof(second) == 'object') { second = false; }
-		if (typeof(millisec) == 'object') { millisec = false; }
-		if (typeof(timezone) == 'object') { timezone = false; }
-
-		if (hour !== false) { hour = parseInt(hour,10); }
-		if (minute !== false) { minute = parseInt(minute,10); }
-		if (second !== false) { second = parseInt(second,10); }
-		if (millisec !== false) { millisec = parseInt(millisec,10); }
-
-		var ampm = o[hour < 12 ? 'amNames' : 'pmNames'][0];
-
-		// If the update was done in the input field, the input field should not be updated.
-		// If the update was done using the sliders, update the input field.
-		var hasChanged = (hour != this.hour || minute != this.minute ||
-				second != this.second || millisec != this.millisec ||
-				(this.ampm.length > 0 &&
-				    (hour < 12) != ($.inArray(this.ampm.toUpperCase(), this.amNames) !== -1)) ||
-				timezone != this.timezone);
-
-		if (hasChanged) {
-
-			if (hour !== false) { this.hour = hour; }
-			if (minute !== false) { this.minute = minute; }
-			if (second !== false) { this.second = second; }
-			if (millisec !== false) { this.millisec = millisec; }
-			if (timezone !== false) { this.timezone = timezone; }
-
-			if (!this.inst) { this.inst = $.datepicker._getInst(this.$input[0]); }
-
-			this._limitMinMaxDateTime(this.inst, true);
-		}
-		if (o.ampm) { this.ampm = ampm; }
-
-		//this._formatTime();
-		this.formattedTime = $.datepicker.formatTime(this._defaults.timeFormat, this, this._defaults);
-		if (this.$timeObj) { this.$timeObj.text(this.formattedTime + o.timeSuffix); }
-		this.timeDefined = true;
-		if (hasChanged) { this._updateDateTime(); }
-	},
-
-	//########################################################################
-	// call custom onSelect.
-	// bind to sliders slidestop, and grid click.
-	//########################################################################
-	_onSelectHandler: function() {
-		var onSelect = this._defaults.onSelect;
-		var inputEl = this.$input ? this.$input[0] : null;
-		if (onSelect && inputEl) {
-			onSelect.apply(inputEl, [this.formattedDateTime, this]);
-		}
-	},
-
-	//########################################################################
-	// left for any backwards compatibility
-	//########################################################################
-	_formatTime: function(time, format) {
-		time = time || { hour: this.hour, minute: this.minute, second: this.second, millisec: this.millisec, ampm: this.ampm, timezone: this.timezone };
-		var tmptime = (format || this._defaults.timeFormat).toString();
-
-		tmptime = $.datepicker.formatTime(tmptime, time, this._defaults);
-
-		if (arguments.length) { return tmptime; }
-		else { this.formattedTime = tmptime; }
-	},
-
-	//########################################################################
-	// update our input with the new date time..
-	//########################################################################
-	_updateDateTime: function(dp_inst) {
-		dp_inst = this.inst || dp_inst;
-		var dt = $.datepicker._daylightSavingAdjust(new Date(dp_inst.selectedYear, dp_inst.selectedMonth, dp_inst.selectedDay)),
-			dateFmt = $.datepicker._get(dp_inst, 'dateFormat'),
-			formatCfg = $.datepicker._getFormatConfig(dp_inst),
-			timeAvailable = dt !== null && this.timeDefined;
-		this.formattedDate = $.datepicker.formatDate(dateFmt, (dt === null ? new Date() : dt), formatCfg);
-		var formattedDateTime = this.formattedDate;
-		// remove following lines to force every changes in date picker to change the input value
-		// Bug descriptions: when an input field has a default value, and click on the field to pop up the date picker. 
-		// If the user manually empty the value in the input field, the date picker will never change selected value.
-		//if (dp_inst.lastVal !== undefined && (dp_inst.lastVal.length > 0 && this.$input.val().length === 0)) {
-		//	return;
-        //}
-
-		if (this._defaults.timeOnly === true) {
-			formattedDateTime = this.formattedTime;
-		} else if (this._defaults.timeOnly !== true && (this._defaults.alwaysSetTime || timeAvailable)) {
-			formattedDateTime += this._defaults.separator + this.formattedTime + this._defaults.timeSuffix;
-		}
-
-		this.formattedDateTime = formattedDateTime;
-
-		if(!this._defaults.showTimepicker) {
-			this.$input.val(this.formattedDate);
-		} else if (this.$altInput && this._defaults.altFieldTimeOnly === true) {
-			this.$altInput.val(this.formattedTime);
-			this.$input.val(this.formattedDate);
-		} else if(this.$altInput) {
-			this.$altInput.val(formattedDateTime);
-			this.$input.val(formattedDateTime);
-		} else {
-			this.$input.val(formattedDateTime);
-		}
-
-		this.$input.trigger("change");
-	}
-
-});
-
-$.fn.extend({
-	//########################################################################
-	// shorthand just to use timepicker..
-	//########################################################################
-	timepicker: function(o) {
-		o = o || {};
-		var tmp_args = arguments;
-
-		if (typeof o == 'object') { tmp_args[0] = $.extend(o, { timeOnly: true }); }
-
-		return $(this).each(function() {
-			$.fn.datetimepicker.apply($(this), tmp_args);
-		});
-	},
-
-	//########################################################################
-	// extend timepicker to datepicker
-	//########################################################################
-	datetimepicker: function(o) {
-		o = o || {};
-		var tmp_args = arguments;
-
-		if (typeof(o) == 'string'){
-			if(o == 'getDate') {
-				return $.fn.datepicker.apply($(this[0]), tmp_args);
-            }
-			else {
-				return this.each(function() {
-					var $t = $(this);
-					$t.datepicker.apply($t, tmp_args);
-				});
-            }
-		}
-		else {
-			return this.each(function() {
-				var $t = $(this);
-				$t.datepicker($.timepicker._newInst($t, o)._defaults);
-			});
-        }
-	}
-});
-
-$.datepicker.parseDateTime = function(dateFormat, timeFormat, dateTimeString, dateSettings, timeSettings) {
-	var parseRes = parseDateTimeInternal(dateFormat, timeFormat, dateTimeString, dateSettings, timeSettings);
-	if (parseRes.timeObj)
-	{
-		var t = parseRes.timeObj;
-		parseRes.date.setHours(t.hour, t.minute, t.second, t.millisec);
-	}
-
-	return parseRes.date;
-};
-
-$.datepicker.parseTime = function(timeFormat, timeString, options) {
-	
-	//########################################################################
-	// pattern for standard and localized AM/PM markers
-	//########################################################################
-	var getPatternAmpm = function(amNames, pmNames) {
-		var markers = [];
-		if (amNames) {
-			$.merge(markers, amNames);
-        }
-		if (pmNames) {
-			$.merge(markers, pmNames);
-        }
-		markers = $.map(markers, function(val) { return val.replace(/[.*+?|()\[\]{}\\]/g, '\\$&'); });
-		return '(' + markers.join('|') + ')?';
-	};
-   
-	//########################################################################
-	// figure out position of time elements.. cause js cant do named captures
-	//########################################################################
-	var getFormatPositions = function( timeFormat ) {
-		var finds = timeFormat.toLowerCase().match(/(h{1,2}|m{1,2}|s{1,2}|l{1}|t{1,2}|z)/g),
-			orders = { h: -1, m: -1, s: -1, l: -1, t: -1, z: -1 };
-
-		if (finds) {
-			for (var i = 0; i < finds.length; i++) {
-				if (orders[finds[i].toString().charAt(0)] == -1) {
-					orders[finds[i].toString().charAt(0)] = i + 1;
-                }
-            }
-        }
-		return orders;
-	};
-    
-	var o = extendRemove(extendRemove({}, $.timepicker._defaults), options || {});
-    
-	var regstr = '^' + timeFormat.toString()
-			.replace(/h{1,2}/ig, '(\\d?\\d)')
-			.replace(/m{1,2}/ig, '(\\d?\\d)')
-			.replace(/s{1,2}/ig, '(\\d?\\d)')
-			.replace(/l{1}/ig, '(\\d?\\d?\\d)')
-			.replace(/t{1,2}/ig, getPatternAmpm(o.amNames, o.pmNames))
-			.replace(/z{1}/ig, '(z|[-+]\\d\\d:?\\d\\d)?')
-			.replace(/\s/g, '\\s?') + o.timeSuffix + '$',
-		order = getFormatPositions(timeFormat),
-		ampm = '',
-		treg;
-
-	treg = timeString.match(new RegExp(regstr, 'i'));
-
-	var resTime = {hour: 0, minute: 0, second: 0, millisec: 0};
-    
-	if (treg) {
-		if (order.t !== -1) {
-			if (treg[order.t] === undefined || treg[order.t].length === 0) {
-				ampm = '';
-				resTime.ampm = '';
-			} else {
-				ampm = $.inArray(treg[order.t], o.amNames) !== -1 ? 'AM' : 'PM';
-				resTime.ampm = o[ampm == 'AM' ? 'amNames' : 'pmNames'][0];
-			}
-		}
-
-		if (order.h !== -1) {
-			if (ampm == 'AM' && treg[order.h] == '12') {
-				resTime.hour = 0; // 12am = 0 hour
-			} else {
-                if (ampm == 'PM' && treg[order.h] != '12') {
-                    resTime.hour = parseInt(treg[order.h],10) + 12; // 12pm = 12 hour, any other pm = hour + 12
-                }
-                else { resTime.hour = Number(treg[order.h]); }
-            }
-		}
-
-		if (order.m !== -1) { resTime.minute = Number(treg[order.m]); }
-		if (order.s !== -1) { resTime.second = Number(treg[order.s]); }
-		if (order.l !== -1) { resTime.millisec = Number(treg[order.l]); }
-		if (order.z !== -1 && treg[order.z] !== undefined) {
-			var tz = treg[order.z].toUpperCase();
-			switch (tz.length) {
-				case 1:	// Z
-					tz = o.timezoneIso8601 ? 'Z' : '+0000';
-					break;
-				case 5:	// +hhmm
-					if (o.timezoneIso8601) {
-						tz = tz.substring(1) == '0000' ?
-							'Z' :
-							tz.substring(0, 3) + ':' + tz.substring(3);
-                    }
-					break;
-				case 6:	// +hh:mm
-					if (!o.timezoneIso8601) {
-						tz = tz == 'Z' || tz.substring(1) == '00:00' ?
-							'+0000' :
-							tz.replace(/:/, '');
-					} else {
-                        if (tz.substring(1) == '00:00') {
-                            tz = 'Z';
-                        }
-                    }
-					break;
-			}
-			resTime.timezone = tz;
-		}
-
-
-		return resTime;
-	}
-
-	return false;
-};
-
-//########################################################################
-// format the time all pretty...
-// format = string format of the time
-// time = a {}, not a Date() for timezones
-// options = essentially the regional[].. amNames, pmNames, ampm
-//########################################################################
-$.datepicker.formatTime = function(format, time, options) {
-	options = options || {};
-	options = $.extend($.timepicker._defaults, options);
-	time = $.extend({hour:0, minute:0, second:0, millisec:0, timezone:'+0000'}, time);
-
-	var tmptime = format;
-	var ampmName = options.amNames[0];
-
-	var hour = parseInt(time.hour, 10);
-	if (options.ampm) {
-		if (hour > 11){
-			ampmName = options.pmNames[0];
-			if(hour > 12) {
-				hour = hour % 12;
-            }
-		}
-		if (hour === 0) {
-			hour = 12;
-        }
-	}
-	tmptime = tmptime.replace(/(?:hh?|mm?|ss?|[tT]{1,2}|[lz])/g, function(match) {
-		switch (match.toLowerCase()) {
-			case 'hh': return ('0' + hour).slice(-2);
-			case 'h':  return hour;
-			case 'mm': return ('0' + time.minute).slice(-2);
-			case 'm':  return time.minute;
-			case 'ss': return ('0' + time.second).slice(-2);
-			case 's':  return time.second;
-			case 'l':  return ('00' + time.millisec).slice(-3);
-			case 'z':  return time.timezone;
-			case 't': case 'tt':
-				if (options.ampm) {
-					if (match.length == 1) {
-						ampmName = ampmName.charAt(0);
-                    }
-					return match.charAt(0) == 'T' ? ampmName.toUpperCase() : ampmName.toLowerCase();
-				}
-				return '';
-		}
-	});
-
-	tmptime = $.trim(tmptime);
-	return tmptime;
-};
-
-//########################################################################
-// the bad hack :/ override datepicker so it doesnt close on select
-// inspired: http://stackoverflow.com/questions/1252512/jquery-datepicker-prevent-closing-picker-when-clicking-a-date/1762378#1762378
-//########################################################################
-$.datepicker._base_selectDate = $.datepicker._selectDate;
-$.datepicker._selectDate = function (id, dateStr) {
-	var inst = this._getInst($(id)[0]),
-		tp_inst = this._get(inst, 'timepicker');
-
-	if (tp_inst) {
-		tp_inst._limitMinMaxDateTime(inst, true);
-		inst.inline = inst.stay_open = true;
-		//This way the onSelect handler called from calendarpicker get the full dateTime
-		this._base_selectDate(id, dateStr);
-		inst.inline = inst.stay_open = false;
-		this._notifyChange(inst);
-		this._updateDatepicker(inst);
-	}
-	else { this._base_selectDate(id, dateStr); }
-};
-
-//#############################################################################################
-// second bad hack :/ override datepicker so it triggers an event when changing the input field
-// and does not redraw the datepicker on every selectDate event
-//#############################################################################################
-$.datepicker._base_updateDatepicker = $.datepicker._updateDatepicker;
-$.datepicker._updateDatepicker = function(inst) {
-
-	// don't popup the datepicker if there is another instance already opened
-	var input = inst.input[0];
-	if($.datepicker._curInst &&
-	   $.datepicker._curInst != inst &&
-	   $.datepicker._datepickerShowing &&
-	   $.datepicker._lastInput != input) {
-		return;
-	}
-
-	if (typeof(inst.stay_open) !== 'boolean' || inst.stay_open === false) {
-
-		this._base_updateDatepicker(inst);
-
-		// Reload the time control when changing something in the input text field.
-		var tp_inst = this._get(inst, 'timepicker');
-		if(tp_inst) {
-			tp_inst._addTimePicker(inst);
-
-			if (tp_inst._defaults.useLocalTimezone) { //checks daylight saving with the new date.
-				var date = new Date(inst.selectedYear, inst.selectedMonth, inst.selectedDay, 12);
-				selectLocalTimeZone(tp_inst, date);
-				tp_inst._onTimeChange();
-			}
-		}
-	}
-};
-
-//#######################################################################################
-// third bad hack :/ override datepicker so it allows spaces and colon in the input field
-//#######################################################################################
-$.datepicker._base_doKeyPress = $.datepicker._doKeyPress;
-$.datepicker._doKeyPress = function(event) {
-	var inst = $.datepicker._getInst(event.target),
-		tp_inst = $.datepicker._get(inst, 'timepicker');
-
-	if (tp_inst) {
-		if ($.datepicker._get(inst, 'constrainInput')) {
-			var ampm = tp_inst._defaults.ampm,
-				dateChars = $.datepicker._possibleChars($.datepicker._get(inst, 'dateFormat')),
-				datetimeChars = tp_inst._defaults.timeFormat.toString()
-								.replace(/[hms]/g, '')
-								.replace(/TT/g, ampm ? 'APM' : '')
-								.replace(/Tt/g, ampm ? 'AaPpMm' : '')
-								.replace(/tT/g, ampm ? 'AaPpMm' : '')
-								.replace(/T/g, ampm ? 'AP' : '')
-								.replace(/tt/g, ampm ? 'apm' : '')
-								.replace(/t/g, ampm ? 'ap' : '') +
-								" " +
-								tp_inst._defaults.separator +
-								tp_inst._defaults.timeSuffix +
-								(tp_inst._defaults.showTimezone ? tp_inst._defaults.timezoneList.join('') : '') +
-								(tp_inst._defaults.amNames.join('')) +
-								(tp_inst._defaults.pmNames.join('')) +
-								dateChars,
-				chr = String.fromCharCode(event.charCode === undefined ? event.keyCode : event.charCode);
-			return event.ctrlKey || (chr < ' ' || !dateChars || datetimeChars.indexOf(chr) > -1);
-		}
-	}
-
-	return $.datepicker._base_doKeyPress(event);
-};
-
-//#######################################################################################
-// Override key up event to sync manual input changes.
-//#######################################################################################
-$.datepicker._base_doKeyUp = $.datepicker._doKeyUp;
-$.datepicker._doKeyUp = function (event) {
-	var inst = $.datepicker._getInst(event.target),
-		tp_inst = $.datepicker._get(inst, 'timepicker');
-
-	if (tp_inst) {
-		if (tp_inst._defaults.timeOnly && (inst.input.val() != inst.lastVal)) {
-			try {
-				$.datepicker._updateDatepicker(inst);
-			}
-			catch (err) {
-				$.datepicker.log(err);
-			}
-		}
-	}
-
-	return $.datepicker._base_doKeyUp(event);
-};
-
-//#######################################################################################
-// override "Today" button to also grab the time.
-//#######################################################################################
-$.datepicker._base_gotoToday = $.datepicker._gotoToday;
-$.datepicker._gotoToday = function(id) {
-	var inst = this._getInst($(id)[0]),
-		$dp = inst.dpDiv;
-	this._base_gotoToday(id);
-	var tp_inst = this._get(inst, 'timepicker');
-	selectLocalTimeZone(tp_inst);
-	var now = new Date();
-	this._setTime(inst, now);
-	$( '.ui-datepicker-today', $dp).click();
-};
-
-//#######################################################################################
-// Disable & enable the Time in the datetimepicker
-//#######################################################################################
-$.datepicker._disableTimepickerDatepicker = function(target) {
-	var inst = this._getInst(target);
-    if (!inst) { return; }
-    
-	var tp_inst = this._get(inst, 'timepicker');
-	$(target).datepicker('getDate'); // Init selected[Year|Month|Day]
-	if (tp_inst) {
-		tp_inst._defaults.showTimepicker = false;
-		tp_inst._updateDateTime(inst);
-	}
-};
-
-$.datepicker._enableTimepickerDatepicker = function(target) {
-	var inst = this._getInst(target);
-    if (!inst) { return; }
-    
-	var tp_inst = this._get(inst, 'timepicker');
-	$(target).datepicker('getDate'); // Init selected[Year|Month|Day]
-	if (tp_inst) {
-		tp_inst._defaults.showTimepicker = true;
-		tp_inst._addTimePicker(inst); // Could be disabled on page load
-		tp_inst._updateDateTime(inst);
-	}
-};
-
-//#######################################################################################
-// Create our own set time function
-//#######################################################################################
-$.datepicker._setTime = function(inst, date) {
-	var tp_inst = this._get(inst, 'timepicker');
-	if (tp_inst) {
-		var defaults = tp_inst._defaults,
-			// calling _setTime with no date sets time to defaults
-			hour = date ? date.getHours() : defaults.hour,
-			minute = date ? date.getMinutes() : defaults.minute,
-			second = date ? date.getSeconds() : defaults.second,
-			millisec = date ? date.getMilliseconds() : defaults.millisec;
-		//check if within min/max times..
-		// correct check if within min/max times. 	
-		// Rewritten by Scott A. Woodward
-		var hourEq = hour === defaults.hourMin,
-			minuteEq = minute === defaults.minuteMin,
-			secondEq = second === defaults.secondMin;
-		var reset = false;
-		if(hour < defaults.hourMin || hour > defaults.hourMax)  
-			reset = true;
-		else if( (minute < defaults.minuteMin || minute > defaults.minuteMax) && hourEq)
-			reset = true;
-		else if( (second < defaults.secondMin || second > defaults.secondMax ) && hourEq && minuteEq)
-			reset = true;
-		else if( (millisec < defaults.millisecMin || millisec > defaults.millisecMax) && hourEq && minuteEq && secondEq)
-			reset = true;
-		if(reset) {
-			hour = defaults.hourMin;
-			minute = defaults.minuteMin;
-			second = defaults.secondMin;
-			millisec = defaults.millisecMin;
-		}
-		tp_inst.hour = hour;
-		tp_inst.minute = minute;
-		tp_inst.second = second;
-		tp_inst.millisec = millisec;
-		if (tp_inst.hour_slider) tp_inst.hour_slider.slider('value', hour);
-		if (tp_inst.minute_slider) tp_inst.minute_slider.slider('value', minute);
-		if (tp_inst.second_slider) tp_inst.second_slider.slider('value', second);
-		if (tp_inst.millisec_slider) tp_inst.millisec_slider.slider('value', millisec);
-
-		tp_inst._onTimeChange();
-		tp_inst._updateDateTime(inst);
-	}
-};
-
-//#######################################################################################
-// Create new public method to set only time, callable as $().datepicker('setTime', date)
-//#######################################################################################
-$.datepicker._setTimeDatepicker = function(target, date, withDate) {
-	var inst = this._getInst(target);
-    if (!inst) { return; }
-    
-	var tp_inst = this._get(inst, 'timepicker');
-    
-	if (tp_inst) {
-		this._setDateFromField(inst);
-		var tp_date;
-		if (date) {
-			if (typeof date == "string") {
-				tp_inst._parseTime(date, withDate);
-				tp_date = new Date();
-				tp_date.setHours(tp_inst.hour, tp_inst.minute, tp_inst.second, tp_inst.millisec);
-			}
-			else { tp_date = new Date(date.getTime()); }
-			if (tp_date.toString() == 'Invalid Date') { tp_date = undefined; }
-			this._setTime(inst, tp_date);
-		}
-	}
-
-};
-
-//#######################################################################################
-// override setDate() to allow setting time too within Date object
-//#######################################################################################
-$.datepicker._base_setDateDatepicker = $.datepicker._setDateDatepicker;
-$.datepicker._setDateDatepicker = function(target, date) {
-	var inst = this._getInst(target);
-    if (!inst) { return; }
-    
-	var tp_date = (date instanceof Date) ? new Date(date.getTime()) : date;
-
-	this._updateDatepicker(inst);
-	this._base_setDateDatepicker.apply(this, arguments);
-	this._setTimeDatepicker(target, tp_date, true);
-};
-
-//#######################################################################################
-// override getDate() to allow getting time too within Date object
-//#######################################################################################
-$.datepicker._base_getDateDatepicker = $.datepicker._getDateDatepicker;
-$.datepicker._getDateDatepicker = function(target, noDefault) {
-	var inst = this._getInst(target);
-    if (!inst) { return; }
-    
-    var tp_inst = this._get(inst, 'timepicker');
-
-	if (tp_inst) {
-		this._setDateFromField(inst, noDefault);
-		var date = this._getDate(inst);
-		if (date && tp_inst._parseTime($(target).val(), tp_inst.timeOnly)) { date.setHours(tp_inst.hour, tp_inst.minute, tp_inst.second, tp_inst.millisec); }
-		return date;
-	}
-	return this._base_getDateDatepicker(target, noDefault);
-};
-
-//#######################################################################################
-// override parseDate() because UI 1.8.14 throws an error about "Extra characters"
-// An option in datapicker to ignore extra format characters would be nicer.
-//#######################################################################################
-$.datepicker._base_parseDate = $.datepicker.parseDate;
-$.datepicker.parseDate = function(format, value, settings) {
-    var splitRes = splitDateTime(format, value, settings);
-	return $.datepicker._base_parseDate(format, splitRes[0], settings);
-};
-
-//#######################################################################################
-// override formatDate to set date with time to the input
-//#######################################################################################
-$.datepicker._base_formatDate = $.datepicker._formatDate;
-$.datepicker._formatDate = function(inst, day, month, year){
-	var tp_inst = this._get(inst, 'timepicker');
-	if(tp_inst) {
-		tp_inst._updateDateTime(inst);
-		return tp_inst.$input.val();
-	}
-	return this._base_formatDate(inst);
-};
-
-//#######################################################################################
-// override options setter to add time to maxDate(Time) and minDate(Time). MaxDate
-//#######################################################################################
-$.datepicker._base_optionDatepicker = $.datepicker._optionDatepicker;
-$.datepicker._optionDatepicker = function(target, name, value) {
-	var inst = this._getInst(target);
-    if (!inst) { return null; }
-    
-	var tp_inst = this._get(inst, 'timepicker');
-	if (tp_inst) {
-		var min = null, max = null, onselect = null;
-		if (typeof name == 'string') { // if min/max was set with the string
-			if (name === 'minDate' || name === 'minDateTime' ) {
-				min = value;
-            }
-			else {
-                if (name === 'maxDate' || name === 'maxDateTime') {
-                    max = value;
-                }
-                else {
-                    if (name === 'onSelect') {
-                        onselect = value;
-                    }
-                }
-            }
-		} else {
-            if (typeof name == 'object') { //if min/max was set with the JSON
-                if (name.minDate) {
-                    min = name.minDate;
-                } else {
-                    if (name.minDateTime) {
-                        min = name.minDateTime;
-                    } else {
-                        if (name.maxDate) {
-                            max = name.maxDate;
-                        } else {
-                            if (name.maxDateTime) {
-                                max = name.maxDateTime;
-                            }
-                        }
-                    }
-                }
-            }
-        }
-		if(min) { //if min was set
-			if (min === 0) {
-				min = new Date();
-            } else {
-				min = new Date(min);
-            }
-
-			tp_inst._defaults.minDate = min;
-			tp_inst._defaults.minDateTime = min;
-		} else if (max) { //if max was set
-			if(max===0) {
-				max=new Date();
-            } else {
-				max= new Date(max);
-            }
-			tp_inst._defaults.maxDate = max;
-			tp_inst._defaults.maxDateTime = max;
-		} else if (onselect) {
-			tp_inst._defaults.onSelect = onselect;
-        }
-	}
-	if (value === undefined) {
-		return this._base_optionDatepicker(target, name);
-    }
-	return this._base_optionDatepicker(target, name, value);
-};
-
-//#######################################################################################
-// jQuery extend now ignores nulls!
-//#######################################################################################
-function extendRemove(target, props) {
-	$.extend(target, props);
-	for (var name in props) {
-		if (props[name] === null || props[name] === undefined) {
-			target[name] = props[name];
-        }
-    }
-	return target;
-}
-
-//#######################################################################################
-// Splits datetime string into date ans time substrings.
-// Throws exception when date can't be parsed
-// If only date is present, time substring eill be '' 
-//#######################################################################################
-var splitDateTime = function(dateFormat, dateTimeString, dateSettings)
-{
-	try {
-		var date = $.datepicker._base_parseDate(dateFormat, dateTimeString, dateSettings);
-	} catch (err) {
-		if (err.indexOf(":") >= 0) {
-			// Hack!  The error message ends with a colon, a space, and
-			// the "extra" characters.  We rely on that instead of
-			// attempting to perfectly reproduce the parsing algorithm.
-            var dateStringLength = dateTimeString.length-(err.length-err.indexOf(':')-2);
-            var timeString = dateTimeString.substring(dateStringLength);
-
-            return [dateTimeString.substring(0, dateStringLength), dateTimeString.substring(dateStringLength)];
-            
-		} else {
-			throw err;
-		}
-	}
-	return [dateTimeString, ''];
-};
-
-//#######################################################################################
-// Internal function to parse datetime interval
-// Returns: {date: Date, timeObj: Object}, where
-//   date - parsed date without time (type Date)
-//   timeObj = {hour: , minute: , second: , millisec: } - parsed time. Optional
-//#######################################################################################
-var parseDateTimeInternal = function(dateFormat, timeFormat, dateTimeString, dateSettings, timeSettings)
-{
-    var date;
-    var splitRes = splitDateTime(dateFormat, dateTimeString, dateSettings);
-	date = $.datepicker._base_parseDate(dateFormat, splitRes[0], dateSettings);
-    if (splitRes[1] !== '')
-    {
-        var timeString = splitRes[1];
-        var separator = timeSettings && timeSettings.separator ? timeSettings.separator : $.timepicker._defaults.separator;            
-        if ( timeString.indexOf(separator) !== 0) {
-            throw 'Missing time separator';
-        }
-        timeString = timeString.substring(separator.length);
-        var parsedTime = $.datepicker.parseTime(timeFormat, timeString, timeSettings);
-        if (parsedTime === null) {
-            throw 'Wrong time format';
-        }
-        return {date: date, timeObj: parsedTime};
-    } else {
-        return {date: date};
-    }
-};
-
-//#######################################################################################
-// Internal function to set timezone_select to the local timezone
-//#######################################################################################
-var selectLocalTimeZone = function(tp_inst, date)
-{
-	if (tp_inst && tp_inst.timezone_select) {
-		tp_inst._defaults.useLocalTimezone = true;
-		var now = typeof date !== 'undefined' ? date : new Date();
-		var tzoffset = timeZoneString(now);
-		if (tp_inst._defaults.timezoneIso8601) {
-			tzoffset = tzoffset.substring(0, 3) + ':' + tzoffset.substring(3);
-        }
-		tp_inst.timezone_select.val(tzoffset);
-	}
-};
-
-// Input: Date Object
-// Output: String with timezone offset, e.g. '+0100'
-var timeZoneString = function(date)
-{
-	var off = date.getTimezoneOffset() * -10100 / 60;
-	var timezone = (off >= 0 ? '+' : '-') + Math.abs(off).toString().substr(1);
-	return timezone;
-};
-
-$.timepicker = new Timepicker(); // singleton instance
-$.timepicker.version = "1.0.1";
-
-})(jQuery);
diff --git a/lib/web/mage/backend/floating-header.js b/lib/web/mage/backend/floating-header.js
index 106f24e6530..f336cb11898 100644
--- a/lib/web/mage/backend/floating-header.js
+++ b/lib/web/mage/backend/floating-header.js
@@ -37,13 +37,18 @@
          * @private
          */
         _create: function() {
-            var title = $(this.options.title).text();
+            var title = $(this.options.title).text(),
+                wrapped = this.element.find('.page-actions-buttons').children();
             this._setVars();
             this._bind();
             this.element.find('script').remove();
+            if (wrapped.length) {
+                wrapped
+                    .unwrap()   // .page-actions-buttons
+                    .unwrap();  // .page-actions-inner
+            }
             this.element.wrapInner($('<div/>', {'class': 'page-actions-buttons'}));
             this.element.wrapInner($('<div/>', {'class': 'page-actions-inner', 'data-title': title}));
-
         },
 
         /**
diff --git a/pub/index.php b/pub/index.php
index 46939880654..c3a588b2f48 100644
--- a/pub/index.php
+++ b/pub/index.php
@@ -30,10 +30,8 @@ use Magento\Framework\App\Filesystem;
 $params = $_SERVER;
 
 $params[Filesystem::PARAM_APP_DIRS][Filesystem::PUB_DIR] = array('uri' => '');
-$params[Filesystem::PARAM_APP_DIRS][Filesystem::PUB_LIB_DIR] = array('uri' => 'lib');
 $params[Filesystem::PARAM_APP_DIRS][Filesystem::MEDIA_DIR] = array('uri' => 'media');
 $params[Filesystem::PARAM_APP_DIRS][Filesystem::STATIC_VIEW_DIR] = array('uri' => 'static');
-$params[Filesystem::PARAM_APP_DIRS][Filesystem::PUB_VIEW_CACHE_DIR] = array('uri' => 'cache');
 $params[Filesystem::PARAM_APP_DIRS][Filesystem::UPLOAD_DIR] = array('uri' => 'media/upload');
 $entryPoint = new \Magento\Framework\App\EntryPoint\EntryPoint(BP, $params);
 $entryPoint->run('Magento\Framework\App\Http');
-- 
GitLab