3 changed files with 127 additions and 2 deletions
@ -0,0 +1,121 @@
|
||||
# AGPLv3 sysmocom s.f.m.c. GmbH |
||||
|
||||
module Spree |
||||
class Calculator::SysmocomScBaseCalculator < Calculator |
||||
|
||||
def total_value_no_tax(o) |
||||
item_total = o.line_items.map(&:amount).sum |
||||
item_total |
||||
end |
||||
|
||||
def total_weight(o) |
||||
weight = 0 |
||||
o.line_items.each do |li| |
||||
weight += li.quantity * li.variant.weight |
||||
end |
||||
return weight |
||||
end |
||||
|
||||
def extract_iso_code(o) |
||||
if o.kind_of?(Spree::Shipment) |
||||
return o.address.country.iso |
||||
end |
||||
return o.ship_address.country.iso |
||||
end |
||||
|
||||
def extract_dst_dadr(o) |
||||
if o.kind_of?(Spree::Shipment) |
||||
return o.address |
||||
end |
||||
return o.ship_address |
||||
end |
||||
|
||||
def cbrt(x) |
||||
return x ** (1.0/3) |
||||
end |
||||
|
||||
def estimate_dimensions(weight_kg, density_kg_per_dm3) |
||||
volume_dm3 = weight_kg.to_f / density_kg_per_dm3.to_f |
||||
volume_cm3 = 1000.0 * volume_dm3 |
||||
# assuming l=3x, w=2x, h1x -> x=6 |
||||
x = cbrt(volume_cm3 / 6) |
||||
return 3.0 * x, 2.0 * x, 1.0 * x |
||||
end |
||||
|
||||
def sc_compute(carrier, service, object) |
||||
# This could be more than an order but not right now |
||||
weight = total_weight(object) |
||||
dst = extract_dst_addr(object) |
||||
length, width, height = estimate_dimensions(weight, 0.5) |
||||
|
||||
quote = Shipcloud::ShipmentQuote.create( |
||||
carrier: carrier, |
||||
service: service, |
||||
to: { |
||||
street: dst.address1, |
||||
zip_code: dst.zipcode, |
||||
city: dst.city, |
||||
country: dst.country.iso, |
||||
}, |
||||
from: { |
||||
street: "Alt-Moabit", |
||||
street_no: "93", |
||||
zip_code: "10559", |
||||
city: "Berlin", |
||||
country: "DE", |
||||
}, |
||||
package: { |
||||
weight: weight, |
||||
width: width, |
||||
length: length, |
||||
height: height, |
||||
}, |
||||
) |
||||
return quote.price |
||||
end |
||||
|
||||
def available?(object) |
||||
# use 'compute' to determine availability |
||||
begin |
||||
price = sc_compute(object) |
||||
rescue => |
||||
return false |
||||
else |
||||
return true |
||||
end |
||||
end |
||||
|
||||
end |
||||
|
||||
|
||||
class Calculator::SysmocomScUpsStdCalculator < SysmocomScBaseCalculator |
||||
def self.description |
||||
I18n.t(:sysmocom_ups_standard) |
||||
end |
||||
|
||||
def compute(object) |
||||
return sc_compute('ups', 'standard') |
||||
end |
||||
end |
||||
|
||||
class Calculator::SysmocomScUpsExpressCalculator < SysmocomScBaseCalculator |
||||
def self.description |
||||
I18n.t(:sysmocom_ups_express) |
||||
end |
||||
|
||||
def compute(object) |
||||
return sc_compute('ups', 'one_day') |
||||
end |
||||
end |
||||
|
||||
class Calculator::SysmocomScUpsExpeditedCalculator < SysmocomScBaseCalculator |
||||
def self.description |
||||
I18n.t(:sysmocom_ups_expedited) |
||||
end |
||||
|
||||
def compute(object) |
||||
return sc_compute('ups', 'ups_expedited') |
||||
end |
||||
end |
||||
|
||||
end |
Loading…
Reference in new issue