'use strict'; /* US - App Module */ var app = angular.module('caseBuilderApp', [ 'caseBuilderCtlr', 'cartRecCtrl', 'cartCtrl', 'apiServices', 'utilServices', 'ngResource', 'ui.router', 'ui.bootstrap.tooltip', 'ui.bootstrap.position', 'ui.bootstrap.bindHtml' ]); app.config(['$stateProvider','$urlRouterProvider', function($stateProvider,$urlRouterProvider) { // For any unmatched url, redirect to / $urlRouterProvider.otherwise("/"); // Now set up the states $stateProvider .state('casebuilder', { views: { 'casebuilder': { templateUrl: "/assets/views/uk/casebuilder/case_builder_modal.html", controller: 'caseBuilderCtlr' }, 'cartRec': { templateUrl: "/assets/views/uk/cart/shopping_rec_cart.html", controller: 'cartRecCtrl' }, 'cart': { templateUrl: "/assets/views/uk/cart/shopping_cart.html", controller: 'cartCtrl' } }, url: "/" }); } ]); 'use strict'; /* Controllers */ var caseBuilderCtlr = angular.module('caseBuilderCtlr', []); caseBuilderCtlr.controller('caseBuilderCtlr', ['$scope', '$rootScope', 'api', 'util', '$location', '$window', function($scope, $rootScope, api, util, $location, $window) { $scope.$on('reInitCaseBuilder', function(event) { $scope.initCasebuilder(); }); // ---------------------- // User Preferences // ---------------------- $scope.setLimit = function(qty) { $scope.error = false; $scope.cb.limit = qty; $scope.cb.fillQty = qty - ($rootScope.currentQty % 15); $scope.cb.fillQty = ($scope.cb.fillQty <= 0) ? qty : $scope.cb.fillQty; for(var i = 0; i < $scope.cb.fillQty; i++){ $scope.cb.wines[i] = { color: 'no', minPrice: 0, maxPrice: 0 }; } // GA Variable - Set Limit var eventLabel = qty +" bottles"; $scope.setGA('Step 1', eventLabel); $scope.next(); }; $scope.newWineList = function(){ $scope.setScreen('load'); $scope.cb.newWines.cartItems = []; $scope.cb.blocked = []; $scope.error = false; for(var i = 0; i < $scope.cb.fillQty; i++){ var items = $scope.filterWines(i); if(items.length === 0){ $scope.setGA('Errors', 'Unfortunately, there are no '+$scope.cb.wines[i].color+' wines between '+$scope.cb.wines[i].minPrice+' and '+$scope.cb.wines[i].maxPrice+'.'); $scope.setScreen('error'); $scope.wineError = { color: ($scope.cb.wines[i].color == 'rose') ? 'rosé' :$scope.cb.wines[i].color, min: $scope.cb.wines[i].minPrice, max: $scope.cb.wines[i].maxPrice }; return; } else { $scope.cb.newWines.cartItems[i] = {'itemCode': items[0].product.skus[0].itemCode, 'quantity': '1'}; $scope.cb.cart.fullList[i] = items[0].product; $scope.cb.cart.fullList[i].userItemDetails = items[0].userItemDetails; $scope.cb.cart.fullList[i].itemCodeSku = items[0].product.skus[0].itemCode; $scope.cb.cart.fullList[i].salesCode = items[0].product.skus[0].salesCode; $scope.cb.blocked.push(items[0].product.skus[0].itemCode); } } api.cartBatch.add($scope.cb.newWines, function(successResult) { }, function(errorResult) { // console.log('error', errorResult); $scope.error = true; $scope.errorMsg = "An error occurred with Case Builder"; }).$promise.then(function(data) { $rootScope.currentQty = data.response.numBottles; $rootScope.$broadcast('newWines',$scope.cb.cart.fullList); $scope.setScreen('confirm'); $rootScope.isFirst = false; $scope.error = true; miniCart.updateCartContents(true); }); }; $scope.filterWines = function(i){ // Filter Out Mixed Cases var items = _.filter($scope.cb.recommendations, function(obj){ return obj.product.mixed != true; }); // Filter by Color Preference items = _.filter(items, function(obj){ return $scope.cb.wines[i].color === obj.product.colourId.toLowerCase(); }); // Remove broken item ** TEMPORARY *** items = _.filter(items, function(obj){ return obj.product.skus.length != 0; }); // Filter by Price Preference items = _.filter(items, function(obj){ // Replace 1st SKU with single bottle var skuLen = obj.product.skus.length if(skuLen > 1) { for(var x = 0; x < skuLen; x++){ var firstLetter = obj.product.skus[x].itemCode.toLowerCase().charAt(0); // Matches UK ('Q' as first character) - use this sku at this index. if(firstLetter === 'q') { obj.product.skus[0] = obj.product.skus[x]; x = skuLen+1; } // Matches US (Number as first character) - use this sku at this index. if(!isNaN(parseInt(firstLetter))) { obj.product.skus[0] = obj.product.skus[x]; x = skuLen+1; } } } return ($scope.cb.wines[i].minPrice <= obj.product.skus[0].salePricePerBottle && $scope.cb.wines[i].maxPrice >= obj.product.skus[0].salePricePerBottle); }); // Filter out wines that are already selected var len = $scope.cb.blocked.length, finalItems = items; for (var i = 0; i < len; i++) { /* jshint ignore:start */ finalItems = _.filter(finalItems, function(obj) { return obj.product.skus[0].itemCode != $scope.cb.blocked[i]; }); /* jshint ignore:end */ } // Sort by highest or shuffle if(finalItems.length) { items = finalItems; items = _.sortBy(items, function(obj){ return -obj.userItemDetails.sortPriority; }); } else { items = _.shuffle(items); } items = items.slice(0,1); return items; } $scope.close = function() { $scope.setGA('Confirm Modal', 'View Updated Cart'); $scope.resetBuilder(); $location.url('/#cart-recommendations'); }; $scope.toggle = function(type, id){ angular.element('.wine-'+type+'-select .btn-toggle').addClass('deactivate'); angular.element('.wine-'+type+'-select .btn-toggle:eq(' + id + ')').removeClass('deactivate'); }; // ---------------------- // Color Settings // ---------------------- $scope.individualColor = function(index, color) { $scope.cb.wines[index].color = color; angular.element('.btn-toggle').removeClass('deactivate'); }; $scope.oneColor = function(color) { for (var i = 0; i < $scope.cb.fillQty; i++) { $scope.cb.wines[i].color = color; } $scope.setGA('Step 2', color + 'Only'); }; $scope.twoColor = function(color1, color2) { var qty1 = ($scope.cb.fillQty % 2 == 0) ? ($scope.cb.fillQty / 2) : (Math.ceil($scope.cb.fillQty / 2)); var i = 0; for (i; i < qty1; i++) { $scope.cb.wines[i].color = color1; } for (i; i < $scope.cb.fillQty; i++) { $scope.cb.wines[i].color = color2; } $scope.setGA('Step 2', color1 + ' & ' + color2); }; $scope.threeColor = function() { var qty1 = ($scope.cb.fillQty % 3 == 0) ? ($scope.cb.fillQty / 3) : (Math.ceil($scope.cb.fillQty / 3)); var qty2 = ($scope.cb.fillQty % 3 == 2) ? (Math.ceil($scope.cb.fillQty / 3)) : (Math.floor($scope.cb.fillQty / 3)); var i = 0; for (i; i < qty1; i++) { $scope.cb.wines[i].color = 'red'; } for (i; i < (qty1 + qty2); i++) { $scope.cb.wines[i].color = 'white'; } for (i; i < $scope.cb.fillQty; i++) { $scope.cb.wines[i].color = 'rose'; } $scope.setGA('Step 2', 'Reds, Whites & Rose'); }; // ---------------------- // Price Settings // ---------------------- $scope.price = function(min,max){ for (var i = 0; i < $scope.cb.fillQty; i++) { $scope.cb.wines[i].maxPrice = max; $scope.cb.wines[i].minPrice = min; } $scope.setGA('Step 3', min +' - '+ max); $scope.priceSelected = true; }; $scope.individualPrice = function(index, minPrice, maxPrice) { $scope.cb.wines[index].minPrice = minPrice; $scope.cb.wines[index].maxPrice = maxPrice; angular.element('.btn-toggle').removeClass('deactivate'); var disabledCheck = _.filter($scope.cb.wines, function(obj){ return obj.minPrice == 0; }); if(!disabledCheck.length){ $scope.priceSelected = true; } }; // ---------------------- // Validation // ---------------------- $scope.validate = function(type) { var step = 'Step '+$scope.counter; if(type == 'color') { $scope.setGA(step, 'Continue'); var x = _.filter($scope.cb.wines, function(obj){ return obj.color === 'no'; }); (x.length > 0) ? $scope.validateError('In order to continue, please select what color wines you would like.') : $scope.next(); } if(type == 'price') { $scope.setGA(step, 'Fill My Case'); var y = _.filter($scope.cb.wines, function(obj){ return obj.maxPrice === 0; }); (y.length > 0) ? $scope.validateError('In order to continue, please select a price range for your wines.') : $scope.newWineList(); } }; $scope.validateError = function(msg){ $scope.error = true; $scope.errorMsg = msg; $scope.setGA('Errors', msg); }; // ---------------------- // Modal Navigation // ---------------------- $scope.setScreen = function(id) { $scope.screen = { q1: false, q2: false, q3: false, load: false, confirm: false, error: false }; $scope.screen[id] = true; }; $scope.next = function() { $scope.counter++; $scope.error = false; var next = 'q'+($scope.counter); $scope.setScreen(next); }; // ---------------------- // Reset Scope Variables // ---------------------- $scope.getRecommendations = function(){ api.recommendations.list({}, function(data) { }, function(errorResult) { // console.log('error'); }) .$promise.then(function(data) { $scope.cb.recommendations = data.response.userItems; $rootScope.wineRecommendations = data.response.userItems; $scope.dataReady = true; if($rootScope.currentQty >= 12){ $scope.setLimit(15); } }); }; $scope.getBrandInfo = function(){ var brand = util.brand(); var obj = {}; switch(brand) { case 'laithwaiteswine': obj = { link: util.unlimitedInfo(brand, $scope.showUnlimited), name: "Laithwaite's Unlimited", shortName: 'law' }; break; case 'virgin': obj = { link: util.unlimitedInfo(brand, $scope.showUnlimited), name: 'Virgin Wines Unlimited', shortName: 'vir' }; break; case 'wsjwine': obj = { link: util.unlimitedInfo(brand, $scope.showUnlimited), name: 'WSJwine Advantage', shortName: 'wsj' }; break; case 'macyswinecellar': obj = { link: util.unlimitedInfo(brand, $scope.showUnlimited), name: 'Macy\'s Wine Cellar Unlimited', shortName: 'mcy' }; break; default: obj = { link: util.unlimitedInfo(brand, $scope.showUnlimited), name: "Laithwaite's Unlimited", shortName: 'law' }; break; } return obj; }; $scope.resetBuilder = function() { $scope.cb = { limit: 0, currentQty: $rootScope.currentQty, fillQty: 0, wines: [], newWines: { cartItems: [] }, cart: { fullList: [] }, recommendations: $rootScope.wineRecommendations }; $scope.counter = 1; $scope.dataReady = false; $scope.modalWidth = 680; $scope.error = false; var q = ($rootScope.currentQty >= 12) ? 'q2' : 'q1'; $scope.setScreen(q); $scope.qtyFlag = false; $scope.priceSelected = false; angular.element('.btn-toggle').removeClass('deactivate'); }; $scope.softReset = function() { $scope.counter = 1; $scope.error = false; $scope.priceSelected = false; var q = ($rootScope.currentQty >= 12) ? 'q2' : 'q1'; $scope.setScreen(q); angular.element('.btn-toggle').removeClass('deactivate'); $scope.cb.wines = []; if($rootScope.currentQty >= 12) { $scope.setLimit(15) } }; $scope.resetColors = function() { for (var i = 0; i < $scope.cb.wines.length; i++) { $scope.cb.wines[i].color = 'no'; } }; $scope.resetPrices = function() { for (var i = 0; i < $scope.cb.wines.length; i++) { $scope.cb.wines[i].minPrice = 0; $scope.cb.wines[i].maxPrice = 0; } }; // Generic GA Send Event - Requires both arguments $scope.setGA = function(action, label) { dataLayer.push({ 'event': 'GAevent', 'eventCategory': 'Casebuilder', 'eventAction': action, 'eventLabel': label }); }; // ---------------------- // Intialize Case Builder // ---------------------- $scope.initCasebuilder = function(){ $scope.resetBuilder(); $scope.setGA('Launch','Fill My Case'); $scope.getRecommendations(); }; $scope.dataReady = false; $scope.qtyFlag = true; $rootScope.isFirst = true; $window.addEventListener('profileLayerLoaded', function(event) { $scope.showUnlimited = util.showUnlimited(); $scope.brand = $scope.getBrandInfo(); }); } ]); /* Controllers */ var cartRecCtrl = angular.module('cartRecCtrl', []); cartRecCtrl.controller('cartRecCtrl', ['$scope', '$rootScope', 'api','util', function($scope, $rootScope, api, util) { $scope.fullWines = []; $scope.wineLength = 0; $scope.country = util.country(); $scope.brandShort = util.brandInfo(util.brand()).shorthand; console.log($scope.brandShort); // START -- IE8 Pollyfill for IndexOf - DO NOT REMOVE if (!Array.prototype.indexOf){ Array.prototype.indexOf = function(elt /*, from*/){ var len = this.length >>> 0; var from = Number(arguments[1]) || 0; from = (from < 0)? Math.ceil(from): Math.floor(from); if (from < 0) from += len; for (; from < len; from++) { if (from in this && this[from] === elt) return from; } return -1; }; } // END -- IE8 Pollyfill for IndexOf - DO NOT REMOVE $scope.$on('newWines', function(event, wineList) { var blocked = []; $scope.newWines = []; $scope.cbWines = []; $scope.newWines = wineList; $scope.removeFlag = false; $scope.fullWines = $scope.fullWines.concat($scope.newWines); $scope.wineLength = $scope.fullWines.length; for(var i=0; i < $scope.wineLength; i++){ var currId = $scope.fullWines[i].id; $scope.fullWines[i].icon = $scope.getIcon($scope.fullWines[i].userItemDetails.recommendationTypeId); var matched = _.filter($scope.fullWines, function(obj){ return obj.id === currId; }); if(blocked.indexOf(currId) === -1) { blocked.push(currId); $scope.fullWines[i].qty = matched.length; $scope.cbWines.push($scope.fullWines[i]); } } }); $scope.getIcon = function(id){ var icon = {}; if ($scope.country === 'uk') { switch(id) { case 100: icon = { className: 'dw-tags', type: 'our bestselling wines' }; break; case 50: icon = { className: 'dw-taste', type: 'our recommendation' }; break; case 40: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 41: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 42: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 43: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 44: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 45: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 46: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 47: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 48: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 49: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 30: icon = { className: 'dw-purchase', type: 'your purchases' }; break; case 20: icon = { className: 'dw-heart', type: 'your favorites' }; break; case 10: icon = { className: 'dw-star', type: 'wines you' + "'" + 've rated' }; break; } } else { switch(id) { case 100: icon = { className: 'dw-tags', type: 'Monthly Specials' }; break; case 50: icon = { className: 'dw-taste', type: 'Tasteography' }; break; case 40: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 41: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 42: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 43: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 44: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 45: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 46: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 47: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 48: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 49: icon = { className: 'dw-pref', type: 'Preferences' }; break; case 30: icon = { className: 'dw-purchase', type: 'Previously Purchased' }; break; case 20: icon = { className: 'dw-heart', type: 'Favorites' }; break; case 10: icon = { className: 'dw-star', type: 'Reviewed' }; break; } } return icon; }; $scope.alternateSelection = function(){ $rootScope.$broadcast('reInitCaseBuilder'); } $scope.removeAll = function() { $scope.removeFlag = true; if($scope.cbWines.length > 0){ ($scope.country === 'uk') ? $scope.removeItem(0, $scope.cbWines[0].itemCodeSku) : $scope.removeItem(0, $scope.cbWines[0].itemCode); } }; // -------- Add to cart -------- $scope.removeItem = function(index, itemcode) { $scope.cbWines[index].removeLoad = true; $scope.currItemCode = itemcode; if ($scope.country === 'uk') { api.cartUK.del({item:itemcode}, function(successResult) { }, function(errorResult) { // console.log('error', errorResult); }).$promise.then(function(data) { var name = $scope.cbWines[index].name; miniCart.updateCartDom(data, true); $scope.cbWines[index].removeLoad = false; $scope.cbWines.splice(index, 1); $rootScope.currentQty = data.response.numBottles; dataLayer.push({ 'event': 'GAevent', 'eventCategory': 'Casebuilder', 'eventAction': ' Item Removal Cart', 'eventLabel': name }); $scope.fullWines = _.filter($scope.fullWines, function(obj){ return obj.skus[0].itemCode != $scope.currItemCode; }); if($scope.cbWines.length === 0) { $rootScope.isFirst = true; $scope.fullWines = []; } if($scope.removeFlag) { $scope.removeAll(); } }); } else { api.cartUS.remove({item:itemcode}, function(successResult) { }, function(errorResult) { // console.log('error', errorResult); }).$promise.then(function(data) { var name = $scope.cbWines[index].name; miniCart.updateCartDom(data, true); $scope.cbWines[index].removeLoad = false; $scope.cbWines.splice(index, 1); $rootScope.currentQty = data.response.numBottles; dataLayer.push({ 'event': 'GAevent', 'eventCategory': 'Casebuilder', 'eventAction': ' Item Removal Cart', 'eventLabel': name }); $scope.fullWines = _.filter($scope.fullWines, function(obj){ return obj.itemCode != itemcode; }); if($scope.cbWines.length === 0) { $rootScope.isFirst = true; $scope.fullWines = []; } if($scope.removeFlag) { $scope.removeAll(); } }); } }; } ]); 'use strict'; /* Controllers */ var cartCtrl = angular.module('cartCtrl', []); cartCtrl.controller('cartCtrl', ['$scope', '$rootScope', 'api','util', '$window', function($scope, $rootScope, api, util, $window) { // ---------------------- // API Calls // ---------------------- $scope.getCart = function(){ $scope.country = util.country(); if ($scope.country === 'uk') { api.cartUK.list({}, function(data) { $rootScope.currentQty = data.response.numBottles; console.log(data.response); if($rootScope.currentQty < 15 && $rootScope.currentQty > 0){ $rootScope.$broadcast('initCaseBuilder'); } }, function(errorResult) { console.log('error'); } ); } else { api.cartUS.list({}, function(data) { $rootScope.currentQty = data.response.numBottles; $rootScope.launchCb = false; if(!$window.hideCb){ if($rootScope.currentQty < 15 && $rootScope.currentQty > 0){ if(pageLayer[0].visitorType !== 'Prospect'){ var hasDontSends = sessionStorage.hasRatings === 'false' ? false : true; var hasFavorites = sessionStorage.hasFavorites === 'false' ? false : true; var hasPrefs = preferencesLayer[0].hasPrefs; var hasRatings = sessionStorage.hasDontSends === 'false' ? false : true; if(hasDontSends || hasFavorites || hasRatings || hasPrefs){ $rootScope.launchCb = true; $rootScope.$broadcast('initCaseBuilder'); } } } } }, function() { console.log('error'); } ); } }; $scope.removeItem = function(index, itemcode) { $scope.wines[index].removeLoad = true; $scope.wines[index].error = false; api.cartUS.remove({item:itemcode}, function(successResult) { }, function(errorResult) { $scope.wines[index].removeLoad = false; $scope.wines[index].error = true; console.log('error', errorResult); }).$promise.then(function(data) { miniCart.updateCartDom(data, true); $scope.wines.splice(index, 1); $rootScope.currentQty = data.response.numBottles; }); }; $scope.updateItem = function(index, itemcode, qty) { $scope.wines[index].updateLoad = true; $scope.wines[index].error = false; api.cartUS.update({item:itemcode, qty:qty}, function(successResult) { }, function(errorResult) { $scope.wines[index].updateLoad = false; $scope.wines[index].error = true; console.log('error', errorResult); }).$promise.then(function(data) { $scope.wines = data.response.lineItems; miniCart.updateCartDom(data, true); $rootScope.currentQty = data.response.numBottles; }); }; $scope.initCart = function(){ $scope.wines = []; }; // ---------------------- // Intialize Cart // ---------------------- $scope.getCart(); } ]); 'use strict'; var apiServices = angular.module('apiServices', []); apiServices.factory("api", function($resource) { return { cartUS: $resource('/api/cart/:action/:itemcode/:item/:qty?method=:method', {}, { 'list': {method: 'GET', params: {action: 'list'}, isArray: false}, 'add': {method: 'PUT', params: {item: '@item', qty: '@qty', itemcode: 'itemcode'}}, 'update': {method: 'PUT', params: {item: '@item', qty: '@qty', method: 'set', itemcode: 'itemcode'}}, 'remove': {method: 'DELETE', params: {item: '@item', itemcode: 'itemcode'}}, 'del': {method: 'PUT', params: {action: 'delete', item: '@item', itemcode: 'itemcode'}}, }), cartLWM: $resource('/api/cart/:action/:salescode/:item/:qty', {}, { 'list': {method: 'GET', params: {action: 'list'}, isArray: false}, 'add': {method: 'PUT', params: {item: '@item', qty: '@qty', salescode: 'salescode'}}, 'remove': {method: 'DELETE', params: {item: '@item', salescode: 'salescode'}}, 'del': {method: 'PUT', params: {action: 'delete', item: '@item', salescode: 'itemcode'}}, }), cartUK: $resource('/api/cart/:action/:itemcode/:item/:qty', {}, { 'list': {method: 'GET', params: {action: 'list'}, isArray: false}, 'add': {method: 'PUT', params: {item: '@item', qty: '@qty', itemcode: 'itemcode'}}, 'remove': {method: 'DELETE', params: {item: '@item', itemcode: 'itemcode'}}, 'del': {method: 'PUT', params: {action: 'delete', item: '@item', itemcode: 'itemcode'}}, }), cartBatch: $resource('/api/cart/:action/itemcode', {}, { 'add': {method: 'POST'} }), cellar: $resource('/api/user/:list/:action/:item', {}, { 'list': {method: 'GET', params: {list:'@list', action: 'list'}, isArray: false}, 'save': {method: 'PUT', params: {list:'@list', item: '@item'}}, 'remove': {method: 'DELETE', params: {list:'@list', item: '@item'}}, 'del': {method: 'PUT', params: {list:'@list', action: 'delete', item: '@item'}} }), favourites: $resource('/api/user/favourites/:action/:item', {}, { 'list': {method: 'GET', params: {action: 'list'}, isArray: false}, 'save': {method: 'PUT', params: {item: '@item'}}, 'remove': {method: 'DELETE', params: {item: '@item'}}, 'del': {method: 'PUT', params: {action: 'delete', item: '@item'}} }), dislike: $resource(' /api/user/donotsenditem/:action/:item', {}, { 'list': {method: 'GET', params: {action: 'list'}, isArray: false}, 'add': {method: 'PUT', params: {item: '@item'}}, 'del': {method: 'PUT', params: {action: 'delete', item: '@item'}} }), purchases: $resource('/api/user/purchases/:action/', {}, { 'list': {method: 'GET', params: {action: 'list'}, isArray: false} }), ratings: $resource('/api/user/ratings/:action/', {}, { 'list': {method: 'GET', params: {action: 'list'}, isArray: false} }), recommendations: $resource('/api/user/recommendations/:action/:mixed', {}, { 'list': {method: 'GET', params: {action: 'list', mixed: '@mixed'}, isArray: false}, }), product: $resource('/api/product/item/:itemcode', {}, { 'list': {method: 'GET', params: {itemcode: '@itemcode'}, isArray: false} }), caseContents: $resource('/api/product/case/:itemcode', {}, { 'list': {method: 'GET', params: {itemcode: '@itemcode'}, isArray: false} }), preferences: $resource('/api/user/preferences/:action/', {}, { 'list': {method: 'GET', params: {action: 'list'}, isArray: false}, 'add': {method: 'POST'} }), offerlist: $resource('/api/itemlist/:name/:locale/:companyCode', {}, { 'list': {method: 'GET', params:{action: 'list'}, isArray: false}, }), notes: $resource('/php/us/tasting_notes.php?brand=:brand', {}, { 'list': {method: 'GET', params:{brand: '@brand'}, isArray: true }, }) }; }); var utilServices = angular.module('utilServices', []); utilServices.factory("util", function() { return { brand: function() { var brand = _.filter([ 'zagat', 'tcmwineclub', 'natgeowine', 'laithwaiteswine', 'virgin', 'wsjwine', 'winepeople', 'australian', 'nprwineclub', 'giltwine', 'bhgwine', 'macyswinecellar', 'laithwaites', 'sundaytimeswineclub', 'bbcgoodfoodwineclub', 'averys', 'bawineclub', 'bawineexplorer' ], function(elem) { return location.host.indexOf(elem) > 0; }); if (brand[0] == 'tcmwineclub' || brand[0] == 'natgeowine' || brand[0] === 'nprwineclub' || brand[0] === 'giltwine' || brand[0] === 'bhgwine') { brand[0] = 'laithwaiteswine'; } return brand[0]; }, brandInfo: function(brand) { var phoneNumber = '1-800-649-4637'; if (brand == 'tcmwineclub' || brand == 'natgeowine' || brand === 'nprwineclub' || brand === 'giltwine' || brand === 'bhgwine') { if (brand === 'giltwine') { phoneNumber = '1-888-997-0317'; } brand = 'laithwaiteswine'; } var obj = { "wsjwine": { name: "WSJwine", phone: "1-877-975-9463", shorthand: "wsj", locale: "en_US_WSJ" }, "laithwaiteswine": { name: "Laithwaite's Wine", phone: phoneNumber, shorthand: "law", locale: "en_US_4S" }, "macyswinecellar": { name: "Macy's Wine Cellar", phone: "1-888-997-0319", shorthand: "mcy", locale: "en_US_MACYS" }, "virgin": { name: "Virgin Wines", phone: "1-866-426-0336", shorthand: "vir", locale: "en_US_Virgin" }, "winepeople": { name: "Wine People", phone: "1300 362 629", shorthand: "wpe", locale: 'en_AU_WP' }, "australian": { name: "The Australian Wine", phone: "1300 765 021", shorthand: "adc", locale: 'en_AU_ADC' }, "laithwaites": { name: "Laithwaite's Wine", phone: "03330 148 198", shorthand: "law", locale: "en_GB_UKLAIT" }, "sundaytimeswineclub": { name: "Sunday Times Wine Club", phone: "03330 142 776", shorthand: "stw", locale: "en_GB_UKCLUB" }, "averys": { name: "Averys of Bristol", phone: "03330 148 208", shorthand: "avy", locale: "en_GB_AVR" }, "bawineclub": { name: "The Wine Explorer", phone: "03330 142 757", shorthand: "ba", locale: "en_GB_UKLAIT" }, "bawineexplorer": { name: "The Wine Explorer", phone: "03330 142 757", shorthand: "ba", locale: "en_GB_UKLAIT" }, "bbcgoodfoodwineclub": { name: "BBC Good Food Wine Club", phone: "03330 148 208", shorthand: "bbc", locale: "en_GB_UKLAIT" } }; return obj[brand]; }, dataAreaId: function() { var dataAreaId; if (dataLayer && dataLayer[0] && dataLayer[0].dataAreaId === 'LWM') { dataAreaId = 'LWM'; } else { dataAreaId = 'UK'; } return dataAreaId; }, country: function() { if (location.host.indexOf('co.uk') > 0) { return 'uk'; } else if (location.host.indexOf('com.au') > 0) { return 'au'; } else if (location.host.indexOf('co.nz') > 0) { return 'nz'; } else { return 'us'; } }, domain: function() { return location.host; }, env: function() { var full = window.location.host; var parts = full.split('.'); return parts[0]; }, showUnlimited: function() { var freeShipProfile = pageLayer[0].fsp; var offerUnlimited = pageLayer[0].ou; if (offerUnlimited === '1' || offerUnlimited === '') { return 'standard'; } else if (offerUnlimited === '2') { return 'promotional'; } else if (offerUnlimited === '3') { return 'half-price'; } else if (freeShipProfile === 'true' || offerUnlimited === '0') { return false; } }, unlimitedInfo: function(brand, unlimitedType) { var obj = { "wsjwine": { unlimited: { "standard": "/product/WSJwine-1-Year-Advantage-Delivery-Membership/15245UL", "promotional": "/product/WSJwine-1-Year-Unlimited-Delivery-Membership/17110UL", "half-price": "/product/WSJwine-1-Year-Unlimited-Delivery-Membership/17111UL" } }, "laithwaiteswine": { unlimited: { "standard": "/product/Laithwaites-1-Year-Unlimited-Delivery-Membership/15145UL", "promotional": "/product/Laithwaites-1-Year-Unlimited-Delivery-Membership/17096UL", "half-price": "/product/Laithwaites-1-Year-Unlimited-Delivery-Membership/17100UL" } }, "virgin": { unlimited: { "standard": "/product/Virgin-Wines-1-Year-Unlimited-Delivery-Membership/15445UL", "promotional": "/product/Virgin-Wines-1-Year-Unlimited-Delivery-Membership/17112UL", "half-price": "/product/Virgin-Wines-1-Year-Unlimited-Delivery-Membership/17113UL" } }, "macyswinecellar": { unlimited: { "standard": "/product/Macy's-1-Year-Unlimited-Delivery-Membership/15545UL", "promotional": "/product/Macy's-1-Year-Unlimited-Delivery-Membership/18015UL", "half-price": "/product/Macy's-1-Year-Unlimited-Delivery-Membership/18016UL" } } } return obj[brand].unlimited[unlimitedType]; }, setGA: function(category, action, label) { dataLayer.push({'event': 'GAevent', 'eventCategory': category, 'eventAction': action, 'eventLabel': label}); return {category: category, action: action, label: label}; } } });