bbmb 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (92) hide show
  1. data/History.txt +5 -0
  2. data/LICENSE.txt +339 -0
  3. data/Manifest.txt +91 -0
  4. data/README.txt +25 -0
  5. data/Rakefile +28 -0
  6. data/bin/admin +71 -0
  7. data/bin/bbmbd +61 -0
  8. data/lib/bbmb.rb +9 -0
  9. data/lib/bbmb/config.rb +106 -0
  10. data/lib/bbmb/html/state/change_password.rb +50 -0
  11. data/lib/bbmb/html/state/current_order.rb +81 -0
  12. data/lib/bbmb/html/state/customer.rb +109 -0
  13. data/lib/bbmb/html/state/customers.rb +52 -0
  14. data/lib/bbmb/html/state/favorites.rb +19 -0
  15. data/lib/bbmb/html/state/favorites_result.rb +21 -0
  16. data/lib/bbmb/html/state/global.rb +62 -0
  17. data/lib/bbmb/html/state/history.rb +95 -0
  18. data/lib/bbmb/html/state/info.rb +23 -0
  19. data/lib/bbmb/html/state/json.rb +16 -0
  20. data/lib/bbmb/html/state/login.rb +76 -0
  21. data/lib/bbmb/html/state/order.rb +21 -0
  22. data/lib/bbmb/html/state/orders.rb +19 -0
  23. data/lib/bbmb/html/state/result.rb +64 -0
  24. data/lib/bbmb/html/state/show_pass.rb +16 -0
  25. data/lib/bbmb/html/state/viral/admin.rb +41 -0
  26. data/lib/bbmb/html/state/viral/customer.rb +143 -0
  27. data/lib/bbmb/html/util/known_user.rb +51 -0
  28. data/lib/bbmb/html/util/multilingual.rb +18 -0
  29. data/lib/bbmb/html/util/session.rb +52 -0
  30. data/lib/bbmb/html/util/validator.rb +55 -0
  31. data/lib/bbmb/html/view/backorder.rb +24 -0
  32. data/lib/bbmb/html/view/change_password.rb +42 -0
  33. data/lib/bbmb/html/view/copyleft.rb +41 -0
  34. data/lib/bbmb/html/view/current_order.rb +482 -0
  35. data/lib/bbmb/html/view/customer.rb +152 -0
  36. data/lib/bbmb/html/view/customers.rb +145 -0
  37. data/lib/bbmb/html/view/favorites.rb +162 -0
  38. data/lib/bbmb/html/view/favorites_result.rb +26 -0
  39. data/lib/bbmb/html/view/foot.rb +21 -0
  40. data/lib/bbmb/html/view/head.rb +32 -0
  41. data/lib/bbmb/html/view/history.rb +60 -0
  42. data/lib/bbmb/html/view/info.rb +33 -0
  43. data/lib/bbmb/html/view/json.rb +20 -0
  44. data/lib/bbmb/html/view/list_prices.rb +51 -0
  45. data/lib/bbmb/html/view/login.rb +46 -0
  46. data/lib/bbmb/html/view/multilingual.rb +17 -0
  47. data/lib/bbmb/html/view/navigation.rb +30 -0
  48. data/lib/bbmb/html/view/order.rb +123 -0
  49. data/lib/bbmb/html/view/orders.rb +50 -0
  50. data/lib/bbmb/html/view/result.rb +107 -0
  51. data/lib/bbmb/html/view/search.rb +28 -0
  52. data/lib/bbmb/html/view/show_pass.rb +60 -0
  53. data/lib/bbmb/html/view/template.rb +61 -0
  54. data/lib/bbmb/model/customer.rb +96 -0
  55. data/lib/bbmb/model/order.rb +255 -0
  56. data/lib/bbmb/model/product.rb +99 -0
  57. data/lib/bbmb/model/promotion.rb +52 -0
  58. data/lib/bbmb/model/quota.rb +27 -0
  59. data/lib/bbmb/model/subject.rb +46 -0
  60. data/lib/bbmb/persistence/none.rb +6 -0
  61. data/lib/bbmb/persistence/odba.rb +42 -0
  62. data/lib/bbmb/persistence/odba/model/customer.rb +47 -0
  63. data/lib/bbmb/persistence/odba/model/order.rb +50 -0
  64. data/lib/bbmb/persistence/odba/model/product.rb +26 -0
  65. data/lib/bbmb/persistence/odba/model/quota.rb +12 -0
  66. data/lib/bbmb/util/invoicer.rb +126 -0
  67. data/lib/bbmb/util/mail.rb +140 -0
  68. data/lib/bbmb/util/multilingual.rb +57 -0
  69. data/lib/bbmb/util/numbers.rb +67 -0
  70. data/lib/bbmb/util/password_generator.rb +44 -0
  71. data/lib/bbmb/util/polling_manager.rb +135 -0
  72. data/lib/bbmb/util/server.rb +159 -0
  73. data/lib/bbmb/util/target_dir.rb +36 -0
  74. data/lib/bbmb/util/transfer_dat.rb +34 -0
  75. data/lib/bbmb/util/updater.rb +27 -0
  76. data/test/data/ydim.yml +2 -0
  77. data/test/model/test_customer.rb +75 -0
  78. data/test/model/test_order.rb +426 -0
  79. data/test/model/test_product.rb +238 -0
  80. data/test/model/test_promotion.rb +40 -0
  81. data/test/stub/persistence.rb +57 -0
  82. data/test/suite.rb +12 -0
  83. data/test/test_bbmb.rb +18 -0
  84. data/test/util/test_invoicer.rb +189 -0
  85. data/test/util/test_mail.rb +359 -0
  86. data/test/util/test_money.rb +71 -0
  87. data/test/util/test_password_generator.rb +27 -0
  88. data/test/util/test_polling_manager.rb +312 -0
  89. data/test/util/test_server.rb +189 -0
  90. data/test/util/test_target_dir.rb +82 -0
  91. data/test/util/test_transfer_dat.rb +45 -0
  92. metadata +190 -0
@@ -0,0 +1,26 @@
1
+ #!/usr/bin/env ruby
2
+ # Html::View::Result -- bbmb.ch -- 21.09.2006 -- hwyss@ywesee.com
3
+
4
+ require 'bbmb/html/view/result'
5
+
6
+ module BBMB
7
+ module Html
8
+ module View
9
+ class FavoritesProducts < Products
10
+ EVENT = :favorite_product
11
+ FORM_NAME = 'products'
12
+ CSS_ID = 'favorites'
13
+ end
14
+ class FavoritesResultComposite < ResultComposite
15
+ COMPONENTS = {
16
+ [0,0] => Search,
17
+ [1,0] => :product_count,
18
+ [0,1] => FavoritesProducts,
19
+ }
20
+ end
21
+ class FavoritesResult < Template
22
+ CONTENT = FavoritesResultComposite
23
+ end
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,21 @@
1
+ #!/usr/bin/env ruby
2
+ # Html::View::Foot -- bbmb.ch -- 15.09.2006 -- hwyss@ywesee.com
3
+
4
+ require 'bbmb/html/view/copyleft'
5
+ require 'bbmb/html/view/navigation'
6
+ require 'htmlgrid/divcomposite'
7
+
8
+ module BBMB
9
+ module Html
10
+ module View
11
+ class Foot < HtmlGrid::DivComposite
12
+ COMPONENTS = {
13
+ [0,0] => Navigation,
14
+ [0,1] => CopyLeft,
15
+ }
16
+ CSS_ID = 'head'
17
+ CSS_ID_MAP = ['navigation']
18
+ end
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,32 @@
1
+ #!/usr/bin/env ruby
2
+ # Html::View::Head -- bbmb.ch -- 15.09.2006 -- hwyss@ywesee.com
3
+
4
+ require 'htmlgrid/divcomposite'
5
+ require 'htmlgrid/image'
6
+
7
+ module BBMB
8
+ module Html
9
+ module View
10
+ class Head < HtmlGrid::DivComposite
11
+ COMPONENTS = {
12
+ [0,0] => :logo,
13
+ [0,2] => 'welcome',
14
+ [0,1] => :logged_in_as, # has float-right, needs to be before 'welcome'
15
+ }
16
+ CSS_ID_MAP = {2 => 'welcome', 1 => 'logged-in-as'}
17
+ def logged_in_as(model)
18
+ if(@session.logged_in?)
19
+ @lookandfeel.lookup(:logged_in_as, @session.user.name)
20
+ end
21
+ end
22
+ def logo(model)
23
+ img = HtmlGrid::Image.new(:logo, model, @session, self)
24
+ link = HtmlGrid::Link.new(:home, model, @session, self)
25
+ link.href = @lookandfeel._event_url(:home)
26
+ link.value = img
27
+ link
28
+ end
29
+ end
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,60 @@
1
+ #!/usr/bin/env ruby
2
+ # Html::View::History -- bbmb.ch -- 03.10.2006 -- hwyss@ywesee.com
3
+
4
+ require 'bbmb/html/view/multilingual'
5
+ require 'bbmb/html/view/template'
6
+
7
+ module BBMB
8
+ module Html
9
+ module View
10
+ class HistoryProducts < HtmlGrid::List
11
+ include Multilingual
12
+ BACKGROUND_ROW = 'bg'
13
+ BACKGROUND_SUFFIX = ''
14
+ COMPONENTS = {
15
+ [0,0] => :order_count,
16
+ [1,0] => :quantity,
17
+ [2,0] => :description,
18
+ [3,0] => :price,
19
+ [4,0] => :total,
20
+ }
21
+ CSS_CLASS = 'list'
22
+ CSS_MAP = {
23
+ [0,0,2]=> 'tiny right',
24
+ [2,0] => 'description',
25
+ [3,0] => 'right',
26
+ [4,0] => 'total',
27
+ }
28
+ CSS_HEAD_MAP = {
29
+ [0,0] => 'right',
30
+ [1,0] => 'right',
31
+ [3,0] => 'right',
32
+ [4,0] => 'right',
33
+ }
34
+ SORT_DEFAULT = :description
35
+ def price(model)
36
+ min, max = model.price_extremes
37
+ if(min == max)
38
+ min
39
+ else
40
+ @lookandfeel.lookup(:price_range, min, max)
41
+ end
42
+ end
43
+ end
44
+ class HistoryComposite < HtmlGrid::DivComposite
45
+ COMPONENTS = {
46
+ [0,0] => HistoryProducts,
47
+ [0,1] => :turnover,
48
+ }
49
+ CSS_MAP = { 1 => 'right' }
50
+ CSS_ID_MAP = { 1 => 'order-total' }
51
+ def turnover(model)
52
+ @lookandfeel.lookup(:history_turnover, model.turnover)
53
+ end
54
+ end
55
+ class History < Template
56
+ CONTENT = HistoryComposite
57
+ end
58
+ end
59
+ end
60
+ end
@@ -0,0 +1,33 @@
1
+ #!/usr/bin/env ruby
2
+ # Html::View::Info -- bbmb.ch -- 30.11.2006 -- hwyss@ywesee.com
3
+
4
+ require 'bbmb/html/view/template'
5
+
6
+ module BBMB
7
+ module Html
8
+ module View
9
+ class InfoComposite < HtmlGrid::DivComposite
10
+ COMPONENTS = {
11
+ [0,0] => '&nbsp;',
12
+ [0,1] => :message,
13
+ }
14
+ CSS_ID_MAP = ['divider']
15
+ CSS_MAP = {
16
+ 1 => 'info',
17
+ }
18
+ def message(model)
19
+ @lookandfeel.lookup(model.message).gsub("\n", '<br>')
20
+ end
21
+ end
22
+ class Info < Template
23
+ CONTENT = InfoComposite
24
+ def http_headers
25
+ headers = super
26
+ headers.store('Refresh',
27
+ "5; URL=#{@lookandfeel._event_url(@model.event)}")
28
+ headers
29
+ end
30
+ end
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,20 @@
1
+ #!/usr/bin/env ruby
2
+ # Html::View::Json -- bbmb.ch -- 26.09.2006 -- hwyss@ywesee.com
3
+
4
+ require 'htmlgrid/component'
5
+ require 'json/objects'
6
+
7
+ module BBMB
8
+ module Html
9
+ module View
10
+ class Json < HtmlGrid::Component
11
+ HTTP_HEADERS = {
12
+ 'Content-Type' => 'text/javascript; charset=UTF-8',
13
+ }
14
+ def to_html(context)
15
+ @model.to_json
16
+ end
17
+ end
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,51 @@
1
+ #!/usr/bin/env ruby
2
+ # Html::View::ListPrices -- bbmb.ch -- 21.09.2006 -- hwyss@ywesee.com
3
+
4
+ module BBMB
5
+ module Html
6
+ module View
7
+ module Vat
8
+ def vat(model)
9
+ if(vat = model.vat)
10
+ sprintf("%.1f%%", vat.to_f)
11
+ end
12
+ end
13
+ end
14
+ module ListPrices
15
+ include Vat
16
+ BACKGROUND_ROW = 'bg'
17
+ BACKGROUND_SUFFIX = ''
18
+ HEAD_OFFSET_STEP = [0,1]
19
+ OFFSET_STEP = [0,2]
20
+ def pricex(model, pricex)
21
+ qval = model.qty_level(pricex)
22
+ pval = model.price_qty(qval)
23
+ if(qval.to_i > 0 && pval.to_f > 0)
24
+ @lookandfeel.lookup(:list_price, qval, pval)
25
+ end
26
+ end
27
+ def price1(model)
28
+ pricex(model, 1)
29
+ end
30
+ def price2(model)
31
+ pricex(model, 2)
32
+ end
33
+ def price3(model)
34
+ pricex(model, 3)
35
+ end
36
+ def price4(model)
37
+ pricex(model, 4)
38
+ end
39
+ def price5(model)
40
+ pricex(model, 5)
41
+ end
42
+ def price6(model)
43
+ pricex(model, 6)
44
+ end
45
+ def price_levels(model)
46
+ price1(model)
47
+ end
48
+ end
49
+ end
50
+ end
51
+ end
@@ -0,0 +1,46 @@
1
+ #!/usr/bin/env ruby
2
+ # Html::View::Login -- bbmb.ch -- 15.09.2006 -- hwyss@ywesee.com
3
+
4
+ require 'bbmb/html/view/template'
5
+ require 'htmlgrid/dojotoolkit'
6
+ require 'htmlgrid/errormessage'
7
+ require 'htmlgrid/form'
8
+ require 'htmlgrid/pass'
9
+
10
+ module BBMB
11
+ module Html
12
+ module View
13
+ class LoginForm < HtmlGrid::Form
14
+ COMPONENTS = {
15
+ [0,0] => :email,
16
+ [0,1] => :pass,
17
+ [1,2] => :submit,
18
+ [0,3] => :new_customer,
19
+ }
20
+ CSS_MAP = { [0,3,2] => 'new-customer' }
21
+ EVENT = :login
22
+ FORM_ID = 'login'
23
+ FORM_NAME = 'login'
24
+ LABELS = true
25
+ SYMBOL_MAP = {
26
+ :pass => HtmlGrid::Pass,
27
+ }
28
+ def new_customer(model)
29
+ link = HtmlGrid::Link.new(:new_customer, model, @session, self)
30
+ link.href = @lookandfeel.lookup(:new_customer_mail)
31
+ link.value = @lookandfeel.lookup(:new_customer_invite)
32
+ link.label = true
33
+ link
34
+ end
35
+ end
36
+ class LoginComposite < HtmlGrid::DivComposite
37
+ COMPONENTS = {
38
+ [0,0] => LoginForm,
39
+ }
40
+ end
41
+ class Login < Template
42
+ CONTENT = LoginComposite
43
+ end
44
+ end
45
+ end
46
+ end
@@ -0,0 +1,17 @@
1
+ #!/usr/bin/env ruby
2
+ # -- de.oddb.org -- 09.08.2007 -- hwyss@ywesee.com
3
+
4
+ require 'bbmb/html/util/multilingual'
5
+
6
+ module BBMB
7
+ module Html
8
+ module View
9
+ module Multilingual
10
+ include Util::Multilingual
11
+ def description(model)
12
+ _(model.description)
13
+ end
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,30 @@
1
+ #!/usr/bin/env ruby
2
+ # Html::View::Navigation -- bbmb.ch -- 18.09.2006 -- hwyss@ywesee.com
3
+
4
+ module BBMB
5
+ module Html
6
+ module View
7
+ class NavigationLink < HtmlGrid::Link
8
+ def init
9
+ unless(@session.event == @name)
10
+ self.href = @lookandfeel._event_url(@name)
11
+ end
12
+ super
13
+ end
14
+ end
15
+ class Navigation < HtmlGrid::DivComposite
16
+ COMPONENTS = {}
17
+ DEFAULT_CLASS = NavigationLink
18
+ def init
19
+ build_navigation
20
+ super
21
+ end
22
+ def build_navigation
23
+ @lookandfeel.navigation.each_with_index { |event, idx|
24
+ components.store([idx,0], event)
25
+ }
26
+ end
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,123 @@
1
+ #!/usr/bin/env ruby
2
+ # Html::View::Order -- bbmb.ch -- 27.09.2006 -- hwyss@ywesee.com
3
+
4
+ require 'bbmb/html/util/multilingual'
5
+ require 'bbmb/html/view/template'
6
+ require 'htmlgrid/labeltext'
7
+
8
+ module BBMB
9
+ module Html
10
+ module View
11
+ class AdditionalInformation < HtmlGrid::Composite
12
+ COMPONENTS = {}
13
+ CSS_CLASS = 'list'
14
+ LABELS = true
15
+ VERTICAL = true
16
+ DEFAULT_CLASS = HtmlGrid::Value
17
+ SYMBOL_MAP = {
18
+ :order_total => HtmlGrid::LabelText,
19
+ }
20
+ def init
21
+ idx = 0
22
+ [:reference, :comment, :priority].each { |key|
23
+ if(@model.send(key))
24
+ components.store([0,idx], key)
25
+ css_map.store([0,idx,1,2], 'additional-info')
26
+ idx += 2
27
+ end
28
+ }
29
+ components.update([0,idx,0] => :order_total, [0,idx,1] => :total)
30
+ css_map.store([0,idx], 'order-total')
31
+ super
32
+ end
33
+ def priority(model)
34
+ item = HtmlGrid::Value.new(:priority, model, @session, self)
35
+ item.value = @lookandfeel.lookup("priority_#{model.priority}")
36
+ item
37
+ end
38
+ def total(model)
39
+ span = HtmlGrid::Span.new(model, @session, self)
40
+ span.css_id = 'total'
41
+ span.value = model.total
42
+ span
43
+ end
44
+ end
45
+ module PositionMethods
46
+ include Util::Multilingual
47
+ def delete_position(model, event)
48
+ link = HtmlGrid::Link.new(:delete, model, @session, self)
49
+ url = @lookandfeel.base_url
50
+ id = model.article_number
51
+ link.href = "javascript:delete_position('#{url}', '#{event}', '#{id}');"
52
+ link
53
+ end
54
+ def position_modifier(model, name, event)
55
+ link = HtmlGrid::Link.new(name, model, @session, self)
56
+ args = {
57
+ 'query' => _(model.description).to_s[/^[^\s]+/]
58
+ }
59
+ link.href = @lookandfeel._event_url(event, args)
60
+ link.value = _(model.send(name))
61
+ link
62
+ end
63
+ end
64
+ class Positions < HtmlGrid::List
65
+ include ListPrices
66
+ CSS_CLASS = 'list'
67
+ if BBMB.config.enable_price_levels
68
+ COMPONENTS = {
69
+ [0,0] => :quantity,
70
+ [1,0] => :description,
71
+ [2,0] => :price_base,
72
+ [3,0] => :price_levels,
73
+ [4,0] => :price2,
74
+ [5,0] => :price3,
75
+ [3,1] => :price4,
76
+ [4,1] => :price5,
77
+ [5,1] => :price6,
78
+ [6,0] => :total,
79
+ }
80
+ CSS_HEAD_MAP = {
81
+ [0,0] => 'right',
82
+ [2,0] => 'right',
83
+ [3,0] => 'right',
84
+ [6,0] => 'right',
85
+ }
86
+ CSS_MAP = {
87
+ [0,0] => 'tiny right',
88
+ [1,0] => 'description',
89
+ [2,0,4,2] => 'right',
90
+ [6,0] => 'total',
91
+ }
92
+ else
93
+ COMPONENTS = {
94
+ [0,0] => :quantity,
95
+ [1,0] => :description,
96
+ [2,0] => :price_base,
97
+ [3,0] => :total,
98
+ }
99
+ CSS_HEAD_MAP = {
100
+ [0,0] => 'right',
101
+ [2,0] => 'right',
102
+ [3,0] => 'right',
103
+ }
104
+ CSS_MAP = {
105
+ [0,0] => 'tiny right',
106
+ [1,0] => 'description',
107
+ [2,0] => 'right',
108
+ [3,0] => 'total',
109
+ }
110
+ end
111
+ end
112
+ class OrderComposite < HtmlGrid::DivComposite
113
+ COMPONENTS = {
114
+ [0,0] => Positions,
115
+ [0,1] => AdditionalInformation,
116
+ }
117
+ end
118
+ class Order < Template
119
+ CONTENT = OrderComposite
120
+ end
121
+ end
122
+ end
123
+ end