CountryPrice_CopyPrices::updateCMSFields()   B
last analyzed

Complexity

Conditions 9
Paths 13

Size

Total Lines 40

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 40
rs 7.7244
c 0
b 0
f 0
cc 9
nc 13
nop 1
1
<?php
2
/**
3
 * a class to copy prices from country A to country
4
 * This can be added to Products, but also to Product Groups
5
 * and other pages ...
6
 *
7
 *
8
 *
9
 */
10
class CountryPrice_CopyPrices extends DataExtension
11
{
12
    private static $db = array(
13
        "AllowCopying" => "Boolean"
14
    );
15
16
    public function updateCMSFields(FieldList $fields)
17
    {
18
        if ($this->owner->ID) {
0 ignored issues
show
Bug introduced by
The property ID does not seem to exist in SS_Object.

An attempt at access to an undefined property has been detected. This may either be a typographical error or the property has been renamed but there are still references to its old name.

If you really want to allow access to undefined properties, you can define magic methods to allow access. See the php core documentation on Overloading.

Loading history...
19
            $page = is_a($this->owner, 'SiteTree'); // We use singleton to skip the different is_a php versions issues
0 ignored issues
show
Unused Code introduced by
$page is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
20
            $tab = 'Root.Countries.Pricing';
21
            $fromCountries = CountryPrice_EcommerceCountry::get_real_countries_list();
22
            //->where('CountryPrice.ObjectClass = \''.$this->owner->ClassName.'\' AND CountryPrice.ObjectID = '.$this->owner->ID.'')
23
            if ($fromCountries && $fromCountries->count()) {
24
                $fromCountriesArray = $fromCountries->map('Code', 'Name')->toArray();
25
            } else {
26
                $fromCountriesArray = array();
27
            }
28
            $allCountries =  EcommerceCountry::get();
29
            $toCountries = array();
30
            foreach ($allCountries as $country) {
31
                $country = CountryPrice_EcommerceCountry::get_real_country($country);
32
                $toCountries[$country->Code] = $country->Name . ($country->DoNotAllowSales ? ' (Sales not allowed)' : '');
33
            }
34
            $countryCurrencies = CountryPrice_EcommerceCurrency::get_currency_per_country();
35
            $link = CountryPrice_CopyPrices_Controller::get_link($this->owner);
0 ignored issues
show
Compatibility introduced by
$this->owner of type object<SS_Object> is not a sub-type of object<DataObject>. It seems like you assume a child class of the class SS_Object 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...
36
            $fields->addFieldToTab(
37
                $tab,
38
                $allowCopyingField = new CheckboxField("AllowCopying", "Allow copying")
39
            );
40
            $allowCopyingField->setRightTitle("Turn this on only when you like to copy a bunch of prices.  Otherwise just leave it turned off to avoid accidental copies and speed up the CMS loading times.");
41
            if (count($fromCountriesArray) && count($toCountries) && $this->owner->AllowCopying) {
0 ignored issues
show
Bug introduced by
The property AllowCopying does not seem to exist in SS_Object.

An attempt at access to an undefined property has been detected. This may either be a typographical error or the property has been renamed but there are still references to its old name.

If you really want to allow access to undefined properties, you can define magic methods to allow access. See the php core documentation on Overloading.

Loading history...
42
                $fields->addFieldsToTab($tab, array(
43
                    new HeaderField('Copy Prices'),
44
                    new DropdownField('From', 'From', $fromCountriesArray),
45
                    new CheckboxSetField('To', 'To', $toCountries),
46
                    new HiddenField('CountryCurrencies', '', Convert::array2json($countryCurrencies)),
47
                    new EcommerceCMSButtonField(
48
                        'UpdatePriceLink',
49
                        $link,
50
                        'Copy Prices'
51
                    )
52
                ));
53
            }
54
        }
55
    }
56
57
    /**
58
     * update all child buyables and the current buyable prices
59
     * based on $fromCountry and applied to ALL $toCountries
60
     * @param  string $fromCountryCode  the country code to copy from
61
     * @param  array  $toCountriesArray  the country code to copy to
62
     */
63
    public function updatePrices($fromCountryCode, array $toCountriesArray)
64
    {
65
        $fromCountryObject = EcommerceCountry::get()->filter(array("Code" => $fromCountryCode));
66
        if ($fromCountryObject) {
67
            $fromCountryObject = CountryPrice_EcommerceCountry::get_real_country($fromCountryObject);
68
        } else {
69
            user_error('From Country is not valid');
70
        }
71
        $currencyObject = $fromCountryObject->EcommerceCurrency();
72
        if ($currencyObject && $currencyObject->Code) {
73
            $values = $this->getUpdatePriceValues($fromCountryCodeA, $currencyObject->Code, array());
0 ignored issues
show
Bug introduced by
The variable $fromCountryCodeA does not exist. Did you mean $fromCountryCode?

This check looks for variables that are accessed but have not been defined. It raises an issue if it finds another variable that has a similar name.

The variable may have been renamed without also renaming all references.

Loading history...
74
            foreach ($toCountriesArray as $toCountryCode) {
75
                $toCountryCode = CountryPrice_EcommerceCountry::get_real_country($toCountryCode)->Code;
76
                foreach ($values as $value) {
77
                    $sqlValues[] = "(NOW(),NOW(),{$value[0]},'$toCountryCode','".$currencyObject->Code."','{$value[1]}',{$value[2]})";
0 ignored issues
show
Coding Style Comprehensibility introduced by
$sqlValues was never initialized. Although not strictly required by PHP, it is generally a good practice to add $sqlValues = array(); before regardless.

Adding an explicit array definition is generally preferable to implicit array definition as it guarantees a stable state of the code.

Let’s take a look at an example:

foreach ($collection as $item) {
    $myArray['foo'] = $item->getFoo();

    if ($item->hasBar()) {
        $myArray['bar'] = $item->getBar();
    }

    // do something with $myArray
}

As you can see in this example, the array $myArray is initialized the first time when the foreach loop is entered. You can also see that the value of the bar key is only written conditionally; thus, its value might result from a previous iteration.

This might or might not be intended. To make your intention clear, your code more readible and to avoid accidental bugs, we recommend to add an explicit initialization $myArray = array() either outside or inside the foreach loop.

Loading history...
78
                }
79
            }
80
            if (isset($sqlValues)) {
81
                $sqlValues = implode(',', $sqlValues);
82
                $sql = "
83
                    INSERT INTO \"CountryPrice\" (\"Created\",\"LastEdited\",\"Price\",\"Country\",\"Currency\",\"ObjectClass\",\"ObjectID\")
84
                    VALUES $sqlValues
85
                    ON DUPLICATE KEY
86
                        UPDATE \"LastEdited\" = VALUES(\"LastEdited\"), \"Price\" = VALUES(\"Price\")";
87
                DB::query($sql);
88
            }
89
        }
90
    }
91
92
    /**
93
     * returns an array of
94
     *  - Price
95
     *  - ClassName
96
     *  - ID
97
     * searches through children, until all all childpages have been added
98
     *
99
     * @param  string $country [description]
0 ignored issues
show
Documentation introduced by
There is no parameter named $country. Did you maybe mean $fromCountryCode?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function. It has, however, found a similar but not annotated parameter which might be a good fit.

Consider the following example. The parameter $ireland is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $ireland
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was changed, but the annotation was not.

Loading history...
100
     * @param  array  $values  [description]
101
     * @return array          [description]
102
     */
103
    public function getUpdatePriceValues($fromCountryCode, $currencyCode, array $values)
104
    {
105
        $fromCountryCode = CountryPrice_EcommerceCountry::get_real_country($fromCountryCode)->Code;
106
        if ($this->owner->hasExtension('CountryPrice_BuyableExtension')) {
107
            $countryPrice = $this->owner->CountryPriceForCountryAndCurrency($fromCountry, $currency);
0 ignored issues
show
Bug introduced by
The variable $fromCountry does not exist. Did you mean $fromCountryCode?

This check looks for variables that are accessed but have not been defined. It raises an issue if it finds another variable that has a similar name.

The variable may have been renamed without also renaming all references.

Loading history...
Bug introduced by
The variable $currency does not exist. Did you mean $currencyCode?

This check looks for variables that are accessed but have not been defined. It raises an issue if it finds another variable that has a similar name.

The variable may have been renamed without also renaming all references.

Loading history...
108
            if ($countryPrice) {
109
                $price = $countryPrice->First()->Price;
110
            } else {
111
                $countryPrices = $this->owner->CountryPriceForCountryAndCurrency($fromCountryCode, $currencyCode, $values);
112
                if ($countryPrices && $countryPrices->count()) {
113
                    $price = $countryPrices->First()->Price;
114
                }
115
            }
116
            if (isset($price)) {
117
                $values[] = array(
118
                    $price,
119
                    $this->owner->ClassName,
0 ignored issues
show
Bug introduced by
The property ClassName does not seem to exist in SS_Object.

An attempt at access to an undefined property has been detected. This may either be a typographical error or the property has been renamed but there are still references to its old name.

If you really want to allow access to undefined properties, you can define magic methods to allow access. See the php core documentation on Overloading.

Loading history...
120
                    $this->owner->ID
0 ignored issues
show
Bug introduced by
The property ID does not seem to exist in SS_Object.

An attempt at access to an undefined property has been detected. This may either be a typographical error or the property has been renamed but there are still references to its old name.

If you really want to allow access to undefined properties, you can define magic methods to allow access. See the php core documentation on Overloading.

Loading history...
121
                );
122
            }
123
        }
124 View Code Duplication
        if ($this->owner->hasExtension('ProductWithVariationDecorator')) {
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...
125
            $variations = $this->owner->Variations();
126
            foreach ($variations as $variation) {
127
                $values = array_merge($values, $variation->getUpdatePriceValues($fromCountryCode, $currencyCode, $values));
128
            }
129
        }
130 View Code Duplication
        if (is_a($this->owner, 'SiteTree')) {
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...
131
            $pages = $this->owner->AllChildren();
132
            if ($pages) {
133
                foreach ($pages as $page) {
134
                    $values = array_merge($values, $page->getUpdatePriceValues($fromCountryCode, $currencyCode, $values));
135
                }
136
            }
137
        }
138
        return $values;
139
    }
140
}
141