diff --git a/config/karma.conf.js b/config/karma.conf.js index e8fc492de..bf9f80305 100644 --- a/config/karma.conf.js +++ b/config/karma.conf.js @@ -63,6 +63,7 @@ module.exports = function(config){ 'public/js/app/home/home-index.js', 'public/js/app/home/controllers/home-ctrl.js', + 'public/js/app/home/services/home-svc.js', 'public/js/app/search/search-index.js', 'public/js/app/search/controllers/search-list-ctrl.js', diff --git a/public/index.html b/public/index.html index 0effbb366..de716108f 100644 --- a/public/index.html +++ b/public/index.html @@ -96,6 +96,8 @@ + + diff --git a/public/js/app/home/controllers/home-ctrl.js b/public/js/app/home/controllers/home-ctrl.js index be1cad42f..e82a58808 100644 --- a/public/js/app/home/controllers/home-ctrl.js +++ b/public/js/app/home/controllers/home-ctrl.js @@ -10,28 +10,36 @@ * license agreement you entered into with hybris. */ -'use strict'; +(function () { + 'use strict'; -angular.module('ds.home') + angular.module('ds.home') + .controller('HomeCtrl', ['$scope', 'HomeSvc', + function ($scope, HomeSvc) { - .controller('HomeCtrl', ['$scope', - function ($scope) { + $scope.carouselInterval = 5000; + $scope.slidesLarge = []; + $scope.slidesSmall = []; + $scope.banner1 = {}; + $scope.banner2 = {}; - $scope.carouselInterval = 5000; + //Get site content data from service + $scope.getSiteContent = function getSiteContent() { + var siteContent = HomeSvc.init(); - $scope.slides = [ - { - id: 'audioBanner', - image: './img/homePg-hero-audio.jpg', - state: 'base.category' - }, - { - id: 'officeBanner', - image: './img/homePg-hero-office.jpg', - state: 'base.category' - } - ]; + $scope.slidesLarge = siteContent.slidesLarge; + $scope.slidesSmall = siteContent.slidesSmall; + $scope.banner1 = siteContent.banner1; + $scope.banner2 = siteContent.banner2; + }; + //Init site content data + $scope.getSiteContent(); - }] -); + //Listen for site change event + $scope.$on('site:updated', function siteUpdated() { + $scope.getSiteContent(); + }); + + }]); +})(); \ No newline at end of file diff --git a/public/js/app/home/directives/site-content-image-directive.js b/public/js/app/home/directives/site-content-image-directive.js new file mode 100644 index 000000000..ec5b35300 --- /dev/null +++ b/public/js/app/home/directives/site-content-image-directive.js @@ -0,0 +1,27 @@ +/** + * [y] hybris Platform + * + * Copyright (c) 2000-2015 hybris AG + * All rights reserved. + * + * This software is the confidential and proprietary information of hybris + * ("Confidential Information"). You shall not disclose such Confidential + * Information and shall use it only in accordance with the terms of the + * license agreement you entered into with hybris. + */ + +(function () { + 'use strict'; + + angular.module('ds.home') + .directive('siteContentImage', function () { + return { + restrict: 'E', + scope: { + image: '=', + id: '@imageId' + }, + templateUrl: 'js/app/home/templates/site-content-image.html' + }; + }); +})(); \ No newline at end of file diff --git a/public/js/app/home/services/home-svc.js b/public/js/app/home/services/home-svc.js new file mode 100644 index 000000000..30b63cf51 --- /dev/null +++ b/public/js/app/home/services/home-svc.js @@ -0,0 +1,108 @@ +/** + * [y] hybris Platform + * + * Copyright (c) 2000-2015 hybris AG + * All rights reserved. + * + * This software is the confidential and proprietary information of hybris + * ("Confidential Information"). You shall not disclose such Confidential + * Information and shall use it only in accordance with the terms of the + * license agreement you entered into with hybris. + */ + +(function () { + 'use strict'; + + angular.module('ds.home') + .service('HomeSvc', ['GlobalData', 'settings', '$state', + function (GlobalData, settings, $state) { + + var homeBannerId = 'homeBanner'; + + /** + * Initializes all site content in objects that can be used in UI + * @return object that contains carousel images and banners + */ + var init = function init() { + var self = this; + var slidesLarge = []; + var slidesSmall = []; + var banner1 = {}; + var banner2 = {}; + var siteContent = GlobalData.getSiteBanners(); + + if (self.siteContentExists(siteContent)) { + if (!!siteContent.topImages && siteContent.topImages.length > 0) { + + for (var i = 0; i < siteContent.topImages.length; i++) { + if (!!siteContent.topImages[i].large && siteContent.topImages[i].large.imageUrl !== '') { + slidesLarge.push({ id: homeBannerId, image: siteContent.topImages[i].large }); + } + + if (!!siteContent.topImages[i].small && siteContent.topImages[i].small.imageUrl !== '') { + slidesSmall.push({ id: homeBannerId, image: siteContent.topImages[i].small }); + } + } + } + banner1 = siteContent.banner1; + banner2 = siteContent.banner2; + } + else { + //Redirect to all products page + $state.go(settings.allProductsState); + } + + return { + slidesLarge: slidesLarge, + slidesSmall: slidesSmall, + banner1: banner1, + banner2: banner2 + }; + }; + + /** + * Checks if there is any site content defined for selected site + * @param siteContent - current site content + * @return true/false value that shows if there is site content for provided site + */ + var siteContentExists = function siteContentExists(siteContent) { + if (!siteContent) { + return false; + } + + if (!!siteContent.topImages) { + for (var i = 0; i < siteContent.topImages.length; i++) { + if (!!siteContent.topImages[i] && + !!siteContent.topImages[i].large && + (siteContent.topImages[i].large.imageUrl !== '' || + siteContent.topImages[i].small.imageUrl !== '')) { + return true; + } + } + } + + if (!!siteContent.banner1 && + !!siteContent.banner1.large && + (siteContent.banner1.large.imageUrl !== '' || + siteContent.banner1.small.imageUrl !== '')) { + return true; + } + + if (!!siteContent.banner2 && !! + !!siteContent.banner2.large && + (siteContent.banner2.large.imageUrl !== '' || + siteContent.banner2.small.imageUrl !== '')) { + return true; + } + + return false; + }; + + return { + init: init, + siteContentExists: siteContentExists + }; + + }]); + +})(); \ No newline at end of file diff --git a/public/js/app/home/templates/home.html b/public/js/app/home/templates/home.html index 0000db001..dfe84f587 100644 --- a/public/js/app/home/templates/home.html +++ b/public/js/app/home/templates/home.html @@ -1,20 +1,37 @@
- - - - - + + + + + + + + +
-
- free gift + + + + + + + -
- flight collection + +
diff --git a/public/js/app/home/templates/site-content-image.html b/public/js/app/home/templates/site-content-image.html new file mode 100644 index 000000000..2c92f495d --- /dev/null +++ b/public/js/app/home/templates/site-content-image.html @@ -0,0 +1,10 @@ + + + diff --git a/public/js/app/shared/services/global-data.js b/public/js/app/shared/services/global-data.js index 65b6405b5..7e60709b8 100644 --- a/public/js/app/shared/services/global-data.js +++ b/public/js/app/shared/services/global-data.js @@ -311,7 +311,7 @@ angular.module('ds.shared') } //Emit site change for cart - $rootScope.$emit('site:updated'); + $rootScope.$broadcast('site:updated'); } }, @@ -358,10 +358,17 @@ angular.module('ds.shared') return null; } }, - - getEmailRegEx: function(){ + + getSiteBanners: function () { + if (!!currentSite && !!currentSite.mixins) { + return currentSite.mixins.siteContentDetails; + } + return null; + }, + + getEmailRegEx: function () { return (/^[a-z0-9!#$%&'*+\/=?^_`{|}~.-]+@[a-z0-9]([a-z0-9-]*[a-z0-9])?(\.[a-z0-9]([a-z0-9-]*[a-z0-9])?)*$/i); - + }, getUserTitles: function () { diff --git a/public/js/app/shared/settings.js b/public/js/app/shared/settings.js index 9947fdf41..c98928747 100644 --- a/public/js/app/shared/settings.js +++ b/public/js/app/shared/settings.js @@ -75,6 +75,7 @@ angular.module('ds.shared') homeState: 'base.home', checkoutState: 'base.checkout.details', + allProductsState: 'base.category', eventSource: { login: 'login', diff --git a/test/e2e/coupon-tests.js b/test/e2e/coupon-tests.js index 920777267..fb1fc2e25 100644 --- a/test/e2e/coupon-tests.js +++ b/test/e2e/coupon-tests.js @@ -58,13 +58,12 @@ describe('coupons:', function () { it('should not allow user to add coupon if not logged in', function () { tu.loadProductIntoCart('1', '$14.92'); tu.clickElement('linkText', 'ADD COUPON CODE'); - tu.sendKeys('id', 'coupon-code', '10PERCENT'); + tu.sendKeys('id', 'coupon-code', 'SIGNEDIN'); tu.clickElement('id', 'apply-coupon'); expect(element(by.binding('couponErrorMessage')).getText()).toEqual('SIGN IN TO USE COUPON CODE'); }); it('should not allow user to add coupon below minimum on cart', function () { - tu.loginHelper('coupon@hybristest.com', 'password'); tu.loadProductIntoCart('1', '$14.92'); tu.clickElement('linkText', 'ADD COUPON CODE'); tu.sendKeys('id', 'coupon-code', '20MINIMUM'); @@ -76,7 +75,6 @@ describe('coupons:', function () { }); it('should not allow user to add coupon with incorrect currency', function () { - tu.loginHelper('coupon@hybristest.com', 'password'); browser.wait(function () { return element(by.xpath(tu.whiteCoffeeMug)).isPresent(); }); @@ -110,7 +108,6 @@ describe('coupons:', function () { }); it('should add percentage off coupon on cart', function () { - tu.loginHelper('coupon@hybristest.com', 'password'); addProductandApplyCoupon('10PERCENT', '$14.92'); verifyCartDetails('1', '$13.77', '-$1.07'); tu.clickElement('id', 'remove-coupon'); @@ -118,7 +115,6 @@ describe('coupons:', function () { }); it('should add dollar off coupon on cart', function () { - tu.loginHelper('coupon@hybristest.com', 'password'); addProductandApplyCoupon('10DOLLAR', '$14.92'); verifyCartDetails('1', '$4.22', '-$10.00'); tu.clickElement('id', 'remove-coupon'); @@ -126,7 +122,6 @@ describe('coupons:', function () { }); it('update coupon totals when item is added and removed from cart', function () { - tu.loginHelper('coupon@hybristest.com', 'password'); addProductandApplyCoupon('10PERCENT', '$14.92'); verifyCartDetails('1', '$13.77', '-$1.07'); tu.clickElement('id', 'continue-shopping'); @@ -157,7 +152,6 @@ describe('coupons:', function () { }); it('should update coupon totals when quantity is changed', function () { - tu.loginHelper('coupon@hybristest.com', 'password'); addProductandApplyCoupon('10PERCENT', '$14.92'); verifyCartDetails('1', '$13.77', '-$1.07'); tu.sendKeys('xpath', tu.cartQuantity, '5'); @@ -169,7 +163,6 @@ describe('coupons:', function () { }); it('should remove coupon on cart', function () { - tu.loginHelper('coupon@hybristest.com', 'password'); addProductandApplyCoupon('10PERCENT', '$14.92'); verifyCartDetails('1', '$13.77', '-$1.07'); tu.clickElement('id', 'remove-coupon') @@ -179,7 +172,6 @@ describe('coupons:', function () { }); it('should not allow user to use expired coupon on cart', function () { - tu.loginHelper('coupon@hybristest.com', 'password'); addProductandApplyCoupon('EXPIRED', '$14.92'); expect(element(by.binding('couponErrorMessage')).getText()).toEqual('COUPON HAS EXPIRED.'); removeFromCart(); diff --git a/test/unit/home/home-ctrl-spec.js b/test/unit/home/home-ctrl-spec.js index 2f3ab8898..b14827078 100644 --- a/test/unit/home/home-ctrl-spec.js +++ b/test/unit/home/home-ctrl-spec.js @@ -1,7 +1,7 @@ /* * [y] hybris Platform * - * Copyright (c) 2000-2014 hybris AG + * Copyright (c) 2000-2015 hybris AG * All rights reserved. * * This software is the confidential and proprietary information of hybris @@ -12,33 +12,72 @@ describe('HomeCtrl Test', function () { - var $scope, $rootScope, $controller; + var $scope, $rootScope, $controller, mockedHomeSvc; - beforeEach(angular.mock.module('ds.home'), function () {}); + beforeEach(angular.mock.module('ds.home'), function () { }); - beforeEach(inject(function(_$rootScope_, _$controller_, _$q_) { + beforeEach(inject(function (_$rootScope_, _$controller_, _$q_) { this.addMatchers({ toEqualData: function (expected) { return angular.equals(this.actual, expected); } }); - $rootScope = _$rootScope_; + $rootScope = _$rootScope_; $scope = _$rootScope_.$new(); $controller = _$controller_; })); - describe('Home Ctrl ', function () { + describe('Home Ctrl - no banners', function () { beforeEach(function () { - homeCtrl = $controller('HomeCtrl', {$scope: $scope, $rootScope: $rootScope}); + mockedHomeSvc = { + init: jasmine.createSpy().andReturn({}), + siteContentExists: jasmine.createSpy().andReturn(false) + }; + homeCtrl = $controller('HomeCtrl', { $scope: $scope, '$rootScope': $rootScope, 'HomeSvc': mockedHomeSvc }); + }); + + it('should not display slides as the slidesLarge and slidesSmall are undefined', function () { + expect($scope.slidesLarge).not.toBeDefined(); + expect($scope.slidesSmall).not.toBeDefined(); + expect($scope.carouselInterval).toBeDefined(); + }); + + }); + + describe('Home Ctrl - banners', function () { + + beforeEach(function () { + mockedHomeSvc = { + init: jasmine.createSpy().andReturn({ + slidesLarge: [], + slidesSmall: [], + banner1: {}, + banner2: {}, + }), + siteContentExists: jasmine.createSpy().andReturn(true) + }; + homeCtrl = $controller('HomeCtrl', { $scope: $scope, '$rootScope': $rootScope, 'HomeSvc': mockedHomeSvc }); }); it('should display slides', function () { - expect($scope.slides).toBeDefined(); + expect($scope.slidesLarge).toBeDefined(); + expect($scope.slidesSmall).toBeDefined(); expect($scope.carouselInterval).toBeDefined(); }); + it('should call init method when navigated to home page', function () { + expect(mockedHomeSvc.init).toHaveBeenCalled(); + }); + + it('should call init method when site:updated event happens', function () { + expect(mockedHomeSvc.init).toHaveBeenCalled(); + + $rootScope.$broadcast('site:updated'); + + expect(mockedHomeSvc.init).toHaveBeenCalled(); + }); }); }); diff --git a/test/unit/home/home-svc-spec.js b/test/unit/home/home-svc-spec.js new file mode 100644 index 000000000..e6b1c759a --- /dev/null +++ b/test/unit/home/home-svc-spec.js @@ -0,0 +1,197 @@ +/* + * [y] hybris Platform + * + * Copyright (c) 2000-2015 hybris AG + * All rights reserved. + * + * This software is the confidential and proprietary information of hybris + * ("Confidential Information"). You shall not disclose such Confidential + * Information and shall use it only in accordance with the terms of the + * license agreement you entered into with hybris. + */ + +describe('HomeSvc Test', function () { + + var $scope, $rootScope, $controller, homeSvc, mockedGlobalData, mockedSettings, mockedState; + + mockedGlobalData = {}; + mockedSettings = {}; + mockedState = { + go: jasmine.createSpy() + }; + + beforeEach(function () { + module('ds.home', function ($provide) { + $provide.value('appConfig', {}); + $provide.value('GlobalData', mockedGlobalData); + $provide.value('$state', mockedState); + }); + }); + + beforeEach(inject(function (_$rootScope_, _$controller_, _$q_, _HomeSvc_) { + + this.addMatchers({ + toEqualData: function (expected) { + return angular.equals(this.actual, expected); + } + }); + $rootScope = _$rootScope_; + $scope = _$rootScope_.$new(); + $controller = _$controller_; + homeSvc = _HomeSvc_; + + console.warn(homeSvc); + })); + + describe('Interface', function () { + + it('should expose correct interface', function () { + expect(homeSvc.init).toBeDefined(); + expect(homeSvc.siteContentExists).toBeDefined(); + }); + + }); + + describe('Init()', function () { + it('should check if site content exists and if not should redirect to all products page', function () { + mockedGlobalData.getSiteBanners = jasmine.createSpy().andReturn({}); + + homeSvc.init(); + + expect(mockedState.go).toHaveBeenCalled(); + }); + + it('should check if site content exists and if yes it should return object with all details', function () { + mockedGlobalData.getSiteBanners = jasmine.createSpy().andReturn({ + topImages: [{ + large: { + imageUrl: 'imgLarge1', hyperlinkUrl: '' + }, + small: { + imageUrl: 'imgSmall1', hyperlinkUrl: '' + } + }, { + large: { + imageUrl: '', hyperlinkUrl: '' + }, + small: { + imageUrl: '', hyperlinkUrl: '' + } + }], + banner1: { + large: { + imageUrl: 'banner1Large', hyperlinkUrl: '' + }, + small: { + imageUrl: 'banner1Small', hyperlinkUrl: '' + } + } + }); + + var returnObj = homeSvc.init(); + + expect(returnObj.slidesLarge).toEqualData([{ id: 'homeBanner', image: { imageUrl: 'imgLarge1', hyperlinkUrl: '' } }]); + expect(returnObj.slidesSmall).toEqualData([{ id: 'homeBanner', image: { imageUrl: 'imgSmall1', hyperlinkUrl: '' } }]); + expect(returnObj.banner1).not.toEqualData({}); + expect(returnObj.banner2).not.toBeDefined(); + + + mockedGlobalData.getSiteBanners = jasmine.createSpy().andReturn({ + banner1: { + large: { + imageUrl: 'banner1Large', hyperlinkUrl: '' + }, + small: { + imageUrl: 'banner1Small', hyperlinkUrl: '' + } + } + }); + + var returnObj = homeSvc.init(); + + expect(returnObj.slidesLarge).toEqualData([]); + expect(returnObj.slidesSmall).toEqualData([]); + expect(returnObj.banner1).not.toEqualData({}); + expect(returnObj.banner2).not.toBeDefined(); + }); + }); + + describe('siteContentExist()', function () { + + it('should return false if site content is not defined', function () { + var result = homeSvc.siteContentExists(); + expect(result).toBe(false); + }); + + it('should check if top images are defined and return true if there is at least one image defined there', function () { + var result = homeSvc.siteContentExists({ + topImages:[{ + large: { + imageUrl: '', hyperlinkUrl: '' + }, + small: { + imageUrl: 'banner1Small', hyperlinkUrl: '' + } + }] + }); + expect(result).toBe(true); + + result = homeSvc.siteContentExists({ + topImages: [{ + large: { + imageUrl: '', hyperlinkUrl: '' + }, + small: { + imageUrl: '', hyperlinkUrl: '' + } + }, { + large: { + imageUrl: '', hyperlinkUrl: '' + }, + small: { + imageUrl: 'banner1Small', hyperlinkUrl: '' + } + }] + }); + expect(result).toBe(true); + + result = homeSvc.siteContentExists({ + banner1: { + large: { + imageUrl: '', hyperlinkUrl: '' + }, + small: { + imageUrl: 'smallUrl', hyperlinkUrl: '' + } + } + }); + expect(result).toBe(true); + + + result = homeSvc.siteContentExists({ + banner2: { + large: { + imageUrl: '', hyperlinkUrl: '' + }, + small: { + imageUrl: 'banner2Small', hyperlinkUrl: '' + } + } + }); + expect(result).toBe(true); + + result = homeSvc.siteContentExists({ + banner2: { + large: { + imageUrl: '', hyperlinkUrl: '' + }, + small: { + imageUrl: '', hyperlinkUrl: '' + } + } + }); + expect(result).toBe(false); + }); + }); + +});