Completed
Push — master ( 888d49...a48248 )
by Nicolaas
01:18
created

RepeatOrderForm::doCreate()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 4
rs 10
c 0
b 0
f 0
cc 1
nc 1
nop 3
1
<?php
2
3
4
class RepeatOrderForm extends Form
5
{
6
7
    private static $number_of_product_alternatives = 0;
8
9
10
    public function __construct($controller, $name, $repeatOrderID = 0, $originatingOrder = 0)
11
    {
12
        $order = null;
13
        //create vs edit
14
        if ($repeatOrderID) {
15
            $repeatOrder = DataObject::get_one('RepeatOrder', "ID = ".$repeatOrderID);
16
            $items = $repeatOrder->OrderItems();
17
        } else {
18
            $repeatOrder = null;
19
            if ($originatingOrder) {
20
                $order = Order::get_by_id_if_can_view($originatingOrder);
21
            }
22
            if (!$order) {
23
                $order = ShoppingCart::current_order();
24
            }
25
            if ($order) {
26
                $items = $order->Items();
27
            } else {
28
                $items = null;
29
            }
30
        }
31
32
        //build fields
33
        $fields = FieldList::create();
34
35
        //products!
36
        if ($items) {
37
            $fields->push(HeaderField::create('ProductsHeader', 'Products'));
38
            $products = Product::get()->filter(["AllowPurchase" => 1]);
39
            $productsMap = $products->map('ID', 'Title')->toArray();
40
            $this->array_unshift_assoc($productsMap, 0, "--- Please select ---");
41
            foreach ($productsMap as $id => $title) {
42
                if ($product = Product::get()->byID($id)) {
43
                    if (!$product->canPurchase()) {
44
                        unset($productsMap[$id]);
45
                    }
46
                }
47
            }
48
            $j = 0;
49
            foreach ($items as $key => $item) {
50
                $j++;
51
                $alternativeItemsMap = $productsMap;
52
                $defaultProductID =  $item->ProductID ? $item->ProductID : $item->BuyableID;
53
                $itemID = $defaultProductID;
54
                unset($alternativeItemsMap[$defaultProductID]);
55
                $fields->push(
56
                    DropdownField::create(
57
                        'Product[ID]['.$itemID.']',
58
                        "Preferred Product #$j",
59
                        $productsMap,
60
                        $defaultProductID
61
                    )
62
                );
63
                $fields->push(
64
                    NumericField::create(
65
                        'Product[Quantity]['.$itemID.']',
66
                        " ... quantity",
67
                        $item->Quantity
68
                    )
69
                );
70
                $altCount = Config::inst()->get('RepeatOrderForm', 'number_of_product_alternatives');
71
                if($altCount > 9) {
72
                    user_error('You can only have up to nine alternatives buyables');
73
                } elseif($altCount > 0) {
74
                    for ($i = 1; $i <= $altCount; $i++) {
75
                        $alternativeField = "Alternative".$i."ID";
76
                        $fields->push(
77
                            DropdownField::create(
78
                                'Product['.$alternativeField.']['.$itemID.']',
79
                                " ... alternative $i",
80
                                $alternativeItemsMap,
81
                                (isset($item->$alternativeField) ? $item->$alternativeField : 0)
82
                            )
83
                        );
84
                    }
85
                }
86
            }
87
        } else {
88
            $fields->push(HeaderField::create('items', 'There are no products in this repeating order'));
89
        }
90
91
        //other details
92
        $fields->push(HeaderField::create('DetailsHeader', 'Repeat Order Details'));
93
        $fields->push(
94
            DropdownField::create(
95
                'PaymentMethod',
96
                'Payment Method',
97
                Config::inst()->get('RepeatOrder', 'payment_methods')
98
            )
99
        );
100
        $startField = DateField::create('Start', 'Start Date');
101
        $startField->setConfig('showcalendar', true);
102
        $fields->push($startField);
103
104
        $endField = DateField::create('End', 'End Date');
105
        $endField->setConfig('showcalendar', true);
106
        $fields->push($endField);
107
108
        $fields->push(
109
            DropdownField::create(
110
                'Period',
111
                'Period',
112
                Config::inst()->get('RepeatOrder', 'period_fields')
113
            )
114
        );
115
        $fields->push(
116
            TextareaField::create('Notes', 'Notes')
117
        );
118
119
        //hidden field
120
        if (isset($order->ID)) {
121
            $fields->push(
122
                HiddenField::create('OrderID', 'OrderID', $order->ID)
123
            );
124
        }
125
        if ($repeatOrder) {
126
            $fields->push(
127
                HiddenField::create('RepeatOrderID', 'RepeatOrderID', $repeatOrder->ID)
128
            );
129
        }
130
131
        //actions
132
        $actions = FieldList::create();
133
        if ($repeatOrder) {
134
            $actions->push(FormAction::create('doSave', 'Save'));
135
        } else {
136
            $actions->push(FormAction::create('doCreate', 'Create'));
137
        }
138
139
        //required fields
140
        $requiredArray = array('Start', 'End', 'Period');
141
        $requiredFields = RequiredFields::create($requiredArray);
142
143
        //make form
144
        parent::__construct($controller, $name, $fields, $actions, $requiredFields);
145
146
        //load data
147
        if ($repeatOrder) {
148
            $this->loadDataFrom(
149
                [
150
                    'Start' => $repeatOrder->Start,
151
                    'End' => $repeatOrder->End,
152
                    'Period' => $repeatOrder->Period,
153
                    'Notes' => $repeatOrder->Notes,
154
                    'PaymentMethod' => $repeatOrder->PaymentMethod,
155
                ]
156
            );
157
        }
158
    }
159
160
    /**
161
     * same as save!
162
     * @param  [type] $data    [description]
0 ignored issues
show
Documentation introduced by
The doc-type [type] could not be parsed: Unknown type name "" at position 0. [(view supported doc-types)

This check marks PHPDoc comments that could not be parsed by our parser. To see which comment annotations we can parse, please refer to our documentation on supported doc-types.

Loading history...
163
     * @param  [type] $form    [description]
0 ignored issues
show
Documentation introduced by
The doc-type [type] could not be parsed: Unknown type name "" at position 0. [(view supported doc-types)

This check marks PHPDoc comments that could not be parsed by our parser. To see which comment annotations we can parse, please refer to our documentation on supported doc-types.

Loading history...
164
     * @param  [type] $request [description]
0 ignored issues
show
Documentation introduced by
The doc-type [type] could not be parsed: Unknown type name "" at position 0. [(view supported doc-types)

This check marks PHPDoc comments that could not be parsed by our parser. To see which comment annotations we can parse, please refer to our documentation on supported doc-types.

Loading history...
165
     * @return [type]          [description]
0 ignored issues
show
Documentation introduced by
The doc-type [type] could not be parsed: Unknown type name "" at position 0. [(view supported doc-types)

This check marks PHPDoc comments that could not be parsed by our parser. To see which comment annotations we can parse, please refer to our documentation on supported doc-types.

Loading history...
166
     */
167
    public function doCreate($data, $form, $request)
168
    {
169
        return $this->doSave($data, $form, $request);
170
    }
171
172
    /**
173
     * Save the changes
174
     */
175
    public function doSave($data, $form, $request)
0 ignored issues
show
Unused Code introduced by
The parameter $request is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
176
    {
177
        $data = Convert::raw2sql($data);
178
        $member = Member::currentUser();
179
        if (!$member) {
180
            $form->sessionMessage('Could not find customer details.', 'bad');
181
            $this->controller->redirectBack();
182
183
            return false;
184
        }
185
        if ($member->IsShopAdmin()) {
186
            $form->sessionMessage('Repeat orders can not be created by Shop Administrators.  Only customers can create repeat orders.', 'bad');
187
            $this->controller->redirectBack();
188
189
            return false;
190
        }
191
        if (isset($data['OrderID'])) {
192
            $order = DataObject::get_one('Order', 'Order.ID = \''.$data['OrderID'].'\' AND MemberID = \''.$member->ID.'\'');
193
            if ($order) {
194
                $repeatOrder = RepeatOrder::create_repeat_order_from_order($order);
0 ignored issues
show
Compatibility introduced by
$order of type object<DataObject> is not a sub-type of object<Order>. It seems like you assume a child class of the class DataObject to be always present.

This check looks for parameters that are defined as one type in their type hint or doc comment but seem to be used as a narrower type, i.e an implementation of an interface or a subclass.

Consider changing the type of the parameter or doing an instanceof check before assuming your parameter is of the expected type.

Loading history...
195
            } else {
196
                $form->sessionMessage('Could not find originating order.', 'bad');
197
                $this->controller->redirectBack();
198
199
                return false;
200
            }
201
        } else {
202
            $repeatOrderID = intval($data['RepeatOrderID']);
203
            $repeatOrder = DataObject::get_one('RepeatOrder', 'RepeatOrder.ID = \''.$repeatOrderID.'\' AND MemberID = \''.$member->ID.'\'');
204
        }
205
        if ($repeatOrder) {
206
            if ($repeatOrderItems = $repeatOrder->OrderItems()) {
207
                foreach ($repeatOrderItems as $repeatOrderItem) {
208
                    $repeatOrderItem->ProductID = $data["Product"]["ID"][$repeatOrderItem->ProductID];
209
                    $repeatOrderItem->Quantity = $data["Product"]["Quantity"][$repeatOrderItem->ProductID];
210
                    $altCount = Config::inst()->get('RepeatOrderForm', 'number_of_product_alternatives');
211
                    for ($i = 1; $i <= $altCount; $i++) {
212
                        $alternativeField = "Alternative".$i."ID";
213
                        $repeatOrderItem->$alternativeField = $data["Product"][$alternativeField][$repeatOrderItem->ProductID];
214
                    }
215
                    $repeatOrderItem->write();
216
                }
217
            }
218
            $params = [];
219 View Code Duplication
            if (isset($data['Start']) && strtotime($data['Start']) > strtotime(Date("Y-m-d"))) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
220
                $params['Start'] = $data['Start'];
221
            } else {
222
                $params["Start"] = Date("Y-m-d");
223
            }
224 View Code Duplication
            if (isset($data['End'])  && strtotime($data['End']) > strtotime($params["Start"])) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
225
                $params['End'] = $data['End'];
226
            } else {
227
                $params["End"] = Date("Y-m-d", strtotime("+1 year"));
228
            }
229
            if (isset($data['Period'])) {
230
                $params['Period'] = $data['Period'];
231
            } else {
232
                $data['Period'] = RepeatOrder::default_period_key();
233
            }
234
            if (isset($data['PaymentMethod'])) {
235
                $params['PaymentMethod'] = $data['PaymentMethod'];
236
            } else {
237
                $data['PaymentMethod'] = RepeatOrder::default_payment_method_key();
238
            }
239
            if (isset($data['Notes'])) {
240
                $params['Notes'] = $data['Notes'];
241
            }
242
            $repeatOrder->update($params);
243
            $repeatOrder->Status = 'Pending';
244
            $repeatOrder->write();
245
        } else {
246
            $form->sessionMessage('Could not find repeat order.', 'bad');
247
            $this->controller->redirectBack();
248
249
            return false;
250
        }
251
        $this->controller->redirect(
252
            RepeatOrdersPage::get_repeat_order_link('view', $repeatOrder->ID)
253
        );
254
255
        return true;
256
    }
257
258
    /**
259
     * add item to the beginning of array
260
     * @param  array $arr [description]
261
     * @param  mixed $key [description]
262
     * @param  mixed $val [description]
263
264
     * @return array
265
     */
266
    private function array_unshift_assoc(&$arr, $key, $val)
267
    {
268
        $arr = array_reverse($arr, true);
269
        $arr[$key] = $val;
270
        $arr = array_reverse($arr, true);
271
272
        return $arr;
273
    }
274
}
275