mirror of
https://github.com/openfoodfoundation/openfoodnetwork
synced 2026-02-27 01:43:22 +00:00
Merge branch 'master' into laura_and_will
This commit is contained in:
@@ -1,10 +1,9 @@
|
||||
Darkswarm.directive "fillVertical", ($window)->
|
||||
# Makes something fill the window vertically. Used on the Google Map.
|
||||
restrict: 'A'
|
||||
|
||||
link: (scope, element, attrs)->
|
||||
setSize = ->
|
||||
element.css "height", ($window.innerHeight - element.offset().top)
|
||||
setSize()
|
||||
|
||||
angular.element($window).bind "resize", ->
|
||||
setSize()
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
Darkswarm.directive "ofnFlash", (flash, $timeout, RailsFlashLoader)->
|
||||
# Mappings between flash types (left) and Foundation classes
|
||||
# Our own flash class. Uses the "flash" service (third party), and a directive
|
||||
# called RailsFlashLoader to render
|
||||
typePairings =
|
||||
info: "info"
|
||||
error: "alert"
|
||||
@@ -13,6 +14,8 @@ Darkswarm.directive "ofnFlash", (flash, $timeout, RailsFlashLoader)->
|
||||
|
||||
link: ($scope, element, attr) ->
|
||||
$scope.flashes = []
|
||||
|
||||
# Callback when a new flash message is pushed to flash service
|
||||
show = (message, type)=>
|
||||
if message
|
||||
$scope.flashes.push({message: message, type: typePairings[type]})
|
||||
@@ -21,5 +24,6 @@ Darkswarm.directive "ofnFlash", (flash, $timeout, RailsFlashLoader)->
|
||||
$scope.delete = ->
|
||||
$scope.flashes.shift()
|
||||
|
||||
# Register our callback (above) with flash service
|
||||
flash.subscribe(show)
|
||||
RailsFlashLoader.initFlash()
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
Darkswarm.directive "ofnFocus", ->
|
||||
# Takes an expression attrs.ofnFocus
|
||||
# Watches value of expression, triggers element.focus() when value is truthy
|
||||
# Used to automatically focus on specific inputs in various circumstances
|
||||
restrict: "A"
|
||||
link: (scope, element, attrs) ->
|
||||
scope.$watch attrs.ofnFocus, ((focus) ->
|
||||
focus and element.focus()
|
||||
return
|
||||
), true
|
||||
|
||||
return
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
Darkswarm.directive "loading", (Loading)->
|
||||
# Triggers a screen-wide "loading" thing when Ajaxy stuff is happening
|
||||
scope: {}
|
||||
restrict: 'E'
|
||||
templateUrl: 'loading.html'
|
||||
@@ -6,5 +7,3 @@ Darkswarm.directive "loading", (Loading)->
|
||||
$scope.Loading = Loading
|
||||
$scope.show = ->
|
||||
$scope.Loading.message?
|
||||
|
||||
link: ($scope, element, attr)->
|
||||
|
||||
@@ -1,16 +1,19 @@
|
||||
Darkswarm.directive "ofnModal", ($modal)->
|
||||
# Generic modal! Uses transclusion so designer-types can do stuff like:
|
||||
# %ofn-modal
|
||||
# CONTENT
|
||||
# Only works for simple cases, so roll your own when necessary!
|
||||
restrict: 'E'
|
||||
replace: true
|
||||
transclude: true
|
||||
scope: {}
|
||||
scope: true
|
||||
template: "<a>{{title}}</a>"
|
||||
|
||||
# Instead of using ng-transclude we compile the transcluded template to a string
|
||||
# This compiled template is sent to the $modal service! Such magic!
|
||||
# In theory we could compile the template directly inside link rather than onclick, but it's performant so meh!
|
||||
link: (scope, elem, attrs, ctrl, transclude)->
|
||||
scope.title = attrs.title
|
||||
contents = null
|
||||
elem.on "click", =>
|
||||
# We're using an isolate scope, which is a child of the original scope
|
||||
# We have to compile the transclude against the original scope, not the isolate
|
||||
transclude scope.$parent, (clone)->
|
||||
contents = clone
|
||||
scope.modalInstance = $modal.open(controller: ctrl, template: contents, scope: scope.$parent)
|
||||
transclude scope, (clone)->
|
||||
scope.modalInstance = $modal.open(controller: ctrl, template: clone, scope: scope)
|
||||
|
||||
@@ -1,7 +1,11 @@
|
||||
Darkswarm.directive "renderSvg", ()->
|
||||
# Magical directive that'll render SVGs from URLs
|
||||
# If only there were a neater way of doing this
|
||||
restrict: 'E'
|
||||
priority: 99
|
||||
template: "<svg-wrapper></svg-wrapper>"
|
||||
|
||||
# Fetch SVG via ajax, inject into page using DOM
|
||||
link: (scope, elem, attr)->
|
||||
if /.svg/.test attr.path # Only do this if we've got an svg
|
||||
$.ajax
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
Darkswarm.directive 'scrollAfterLoad', ($timeout, $location, $document)->
|
||||
# Scroll to an element on page load
|
||||
restrict: "A"
|
||||
link: (scope, element, attr) ->
|
||||
if scope.$last is true
|
||||
|
||||
@@ -1,4 +1,6 @@
|
||||
Darkswarm.directive "ofnScrollTo", ($location, $anchorScroll)->
|
||||
# Onclick sets $location.hash to attrs.ofnScrollTo
|
||||
# Then triggers anchorScroll
|
||||
restrict: 'A'
|
||||
link: (scope, element, attrs)->
|
||||
element.bind 'click', (ev)->
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
Darkswarm.directive "shippingTypeSelector", (FilterSelectorsService)->
|
||||
# Builds selector for shipping types
|
||||
restrict: 'E'
|
||||
replace: true
|
||||
templateUrl: 'shipping_type_selector.html'
|
||||
|
||||
@@ -1,4 +1,6 @@
|
||||
Darkswarm.directive "taxonSelector", (FilterSelectorsService)->
|
||||
# Automatically builds activeSelectors for taxons
|
||||
# Lots of magic here
|
||||
restrict: 'E'
|
||||
replace: true
|
||||
scope:
|
||||
@@ -8,7 +10,7 @@ Darkswarm.directive "taxonSelector", (FilterSelectorsService)->
|
||||
|
||||
link: (scope, elem, attr)->
|
||||
selectors_by_id = {}
|
||||
selectors = ["foo"]
|
||||
selectors = null # To get scoping/closure right
|
||||
|
||||
scope.emit = ->
|
||||
scope.results = selectors.filter (selector)->
|
||||
@@ -16,6 +18,7 @@ Darkswarm.directive "taxonSelector", (FilterSelectorsService)->
|
||||
.map (selector)->
|
||||
selector.taxon.id
|
||||
|
||||
# Build hash of unique taxons, each of which gets an ActiveSelector
|
||||
scope.selectors = ->
|
||||
taxons = {}
|
||||
selectors = []
|
||||
@@ -25,7 +28,11 @@ Darkswarm.directive "taxonSelector", (FilterSelectorsService)->
|
||||
if object.supplied_taxons
|
||||
for taxon in object.supplied_taxons
|
||||
taxons[taxon.id] = taxon
|
||||
|
||||
|
||||
# Generate a selector for each taxon.
|
||||
# NOTE: THESE ARE MEMOIZED to stop new selectors from being created constantly, otherwise function always returns non-identical results
|
||||
# This means the $digest cycle can never close and times out
|
||||
# See http://stackoverflow.com/questions/19306452/how-to-fix-10-digest-iterations-reached-aborting-error-in-angular-1-2-fil
|
||||
for id, taxon of taxons
|
||||
if selector = selectors_by_id[id]
|
||||
selectors.push selector
|
||||
|
||||
@@ -1,8 +0,0 @@
|
||||
Spree::Image.class_eval do
|
||||
has_attached_file :attachment,
|
||||
:styles => { :mini => '48x48>', :small => '114x114#', :product => '240x240>', :large => '600x600>' },
|
||||
:default_style => :product,
|
||||
:url => '/spree/products/:id/:style/:basename.:extension',
|
||||
:path => ':rails_root/public/spree/products/:id/:style/:basename.:extension',
|
||||
:convert_options => { :all => '-strip -auto-orient -quality 75' }
|
||||
end
|
||||
@@ -1,6 +1,6 @@
|
||||
class Api::AddressSerializer < ActiveModel::Serializer
|
||||
cached
|
||||
delegate :cache_key, to: :object
|
||||
#cached
|
||||
#delegate :cache_key, to: :object
|
||||
|
||||
attributes :id, :zipcode, :city, :state_name, :state_id,
|
||||
:phone, :firstname, :lastname, :address1, :address2, :city, :country_id,
|
||||
|
||||
@@ -8,13 +8,11 @@
|
||||
|
||||
|
||||
require 'spree/product_filters'
|
||||
require 'open_food_network/searcher'
|
||||
|
||||
Spree.config do |config|
|
||||
config.shipping_instructions = true
|
||||
config.checkout_zone = 'Australia'
|
||||
config.address_requires_state = true
|
||||
config.searcher_class = OpenFoodNetwork::Searcher
|
||||
|
||||
# 12 should be Australia. Hardcoded for CI (Jenkins), where countries are not pre-loaded.
|
||||
config.default_country_id = 12
|
||||
|
||||
@@ -1,37 +0,0 @@
|
||||
require 'spree/core/search/base'
|
||||
|
||||
module OpenFoodNetwork
|
||||
class Searcher < Spree::Core::Search::Base
|
||||
|
||||
# Do not perform pagination
|
||||
def retrieve_products
|
||||
@products_scope = get_base_scope
|
||||
curr_page = page || 1
|
||||
|
||||
@products = @products_scope.includes([:master])
|
||||
end
|
||||
|
||||
def get_base_scope
|
||||
base_scope = super
|
||||
|
||||
# The concern of separating products by distributor and order cycle is dealt with in
|
||||
# a few other places: OpenFoodNetwork::SplitProductsByDistribution (for splitting the main
|
||||
# product display) and Spree::BaseHelper decorator (for taxon counts).
|
||||
|
||||
base_scope = base_scope.in_supplier_or_distributor(enterprise_id) if enterprise_id
|
||||
base_scope = base_scope.in_supplier(supplier_id) if supplier_id
|
||||
base_scope = base_scope.in_distributor(distributor_id) if distributor_id
|
||||
|
||||
base_scope
|
||||
end
|
||||
|
||||
|
||||
def prepare(params)
|
||||
super(params)
|
||||
@properties[:enterprise_id] = params[:enterprise_id]
|
||||
@properties[:supplier_id] = params[:supplier_id]
|
||||
@properties[:distributor_id] = params[:distributor_id]
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
@@ -1,52 +0,0 @@
|
||||
require 'spec_helper'
|
||||
require 'open_food_network/searcher'
|
||||
|
||||
module OpenFoodNetwork
|
||||
describe Searcher do
|
||||
it "searches by supplier" do
|
||||
# Given products under two suppliers
|
||||
s1 = create(:supplier_enterprise)
|
||||
s2 = create(:supplier_enterprise)
|
||||
p1 = create(:product, :supplier => s1)
|
||||
p2 = create(:product, :supplier => s2)
|
||||
|
||||
# When we search for one supplier, we should see only products from that supplier
|
||||
searcher = Searcher.new(:supplier_id => s1.id.to_s)
|
||||
products = searcher.retrieve_products
|
||||
products.should == [p1]
|
||||
end
|
||||
|
||||
it "searches by distributor" do
|
||||
# Given products under two distributors
|
||||
d1 = create(:distributor_enterprise)
|
||||
d2 = create(:distributor_enterprise)
|
||||
p1 = create(:product, :distributors => [d1])
|
||||
p2 = create(:product, :distributors => [d2])
|
||||
|
||||
# When we search for one distributor, we should see only products from that distributor
|
||||
searcher = Searcher.new(:distributor_id => d1.id.to_s)
|
||||
products = searcher.retrieve_products
|
||||
products.should == [p1]
|
||||
end
|
||||
|
||||
it "searches by supplier or distributor" do
|
||||
# Given products under some suppliers and distributors
|
||||
s0 = create(:supplier_enterprise)
|
||||
s1 = create(:supplier_enterprise)
|
||||
d1 = create(:distributor_enterprise)
|
||||
p1 = create(:product, :supplier => s1)
|
||||
p2 = create(:product, :distributors => [d1])
|
||||
p3 = create(:product, :supplier => s0)
|
||||
|
||||
# When we search by the supplier enterprise, we should see the supplied products
|
||||
searcher = Searcher.new(:enterprise_id => s1.id.to_s)
|
||||
products = searcher.retrieve_products
|
||||
products.should == [p1]
|
||||
|
||||
# When we search by the distributor enterprise, we should see the distributed products
|
||||
searcher = Searcher.new(:enterprise_id => d1.id.to_s)
|
||||
products = searcher.retrieve_products
|
||||
products.should == [p2]
|
||||
end
|
||||
end
|
||||
end
|
||||
Reference in New Issue
Block a user