Completed
Push — master ( dc665d...111f9f )
by Nicolaas
03:48
created

augmentValidURLSegment()   A

Complexity

Conditions 3
Paths 3

Size

Total Lines 11
Code Lines 7

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 3
eloc 7
nc 3
nop 0
dl 0
loc 11
rs 9.4285
c 0
b 0
f 0
1
<?php
2
3
/**
4
 * @description: adds a few functions to SiteTree to give each page
5
 * some e-commerce related functionality.
6
 *
7
 *
8
 *
9
 * @authors: Nicolaas [at] Sunny Side Up .co.nz
10
 * @package: ecommerce
11
 * @sub-package: extensions
12
 * @inspiration: Silverstripe Ltd, Jeremy
13
 **/
14
class EcommerceSiteTreeExtension extends SiteTreeExtension
0 ignored issues
show
Coding Style Compatibility introduced by
PSR1 recommends that each class must be in a namespace of at least one level to avoid collisions.

You can fix this by adding a namespace to your class:

namespace YourVendor;

class YourClass { }

When choosing a vendor namespace, try to pick something that is not too generic to avoid conflicts with other libraries.

Loading history...
15
{
16
    /**
17
     * returns the instance of EcommerceConfigAjax for use in templates.
18
     * In templates, it is used like this:
19
     * $AJAXDefinitions.TableID.
20
     *
21
     * @return EcommerceConfigAjax
0 ignored issues
show
Documentation introduced by
Should the return type not be EcommerceConfigAjaxDefinitions?

This check compares the return type specified in the @return annotation of a function or method doc comment with the types returned by the function and raises an issue if they mismatch.

Loading history...
22
     **/
23
    public function AJAXDefinitions()
24
    {
25
        return EcommerceConfigAjax::get_one($this->owner);
26
    }
27
28
    /**
29
     * @return EcommerceDBConfig
30
     **/
31
    public function EcomConfig()
32
    {
33
        return EcommerceDBConfig::current_ecommerce_db_config();
34
    }
35
36
    /**
37
     * tells us if the current page is part of e-commerce.
38
     *
39
     * @return bool
40
     */
41
    public function IsEcommercePage()
42
    {
43
        return false;
44
    }
45
46
    /**
47
     * Log in link.
48
     *
49
     * @return string
50
     */
51
    public function EcommerceLogInLink()
52
    {
53
        if ($this->owner->IsEcommercePage()) {
54
            $link = $this->owner->Link();
55
        } else {
56
            $link = $this->EcomConfig()->AccountPageLink();
57
        }
58
59
        return '/Security/login?BackURL='.urlencode($link);
60
    }
61
62
    function augmentValidURLSegment()
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
63
    {
64
        if($this->owner->IsEcommercePage()) {
65
            $checkForDuplicatesURLSegments = SiteTree::get()
66
                ->filter(array('URLSegment' => $this->URLSegment))
0 ignored issues
show
Bug introduced by
The property URLSegment does not exist. Did you maybe forget to declare it?

In PHP it is possible to write to properties without declaring them. For example, the following is perfectly valid PHP code:

class MyClass { }

$x = new MyClass();
$x->foo = true;

Generally, it is a good practice to explictly declare properties to avoid accidental typos and provide IDE auto-completion:

class MyClass {
    public $foo;
}

$x = new MyClass();
$x->foo = true;
Loading history...
67
                ->exclude(array('ID' => $this->ID));
0 ignored issues
show
Bug introduced by
The property ID does not exist. Did you maybe forget to declare it?

In PHP it is possible to write to properties without declaring them. For example, the following is perfectly valid PHP code:

class MyClass { }

$x = new MyClass();
$x->foo = true;

Generally, it is a good practice to explictly declare properties to avoid accidental typos and provide IDE auto-completion:

class MyClass {
    public $foo;
}

$x = new MyClass();
$x->foo = true;
Loading history...
68
            if($checkForDuplicatesURLSegments->count() > 0) {
69
                return false;
70
            }
71
        }
72
    }
73
74
}
75
76
class EcommerceSiteTreeExtension_Controller extends Extension
0 ignored issues
show
Coding Style Compatibility introduced by
PSR1 recommends that each class should be in its own file to aid autoloaders.

Having each class in a dedicated file usually plays nice with PSR autoloaders and is therefore a well established practice. If you use other autoloaders, you might not want to follow this rule.

Loading history...
Coding Style Compatibility introduced by
PSR1 recommends that each class must be in a namespace of at least one level to avoid collisions.

You can fix this by adding a namespace to your class:

namespace YourVendor;

class YourClass { }

When choosing a vendor namespace, try to pick something that is not too generic to avoid conflicts with other libraries.

Loading history...
77
{
78
    /**
79
     * standard SS method.
80
     * Runs before the Page::init method is called.
81
     */
82
    public function onBeforeInit()
83
    {
84
        //$this->secureHostSwitcher();
0 ignored issues
show
Unused Code Comprehensibility introduced by
84% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
85
86
        Requirements::javascript(THIRDPARTY_DIR.'/jquery/jquery.js');
87
        //Requirements::block(THIRDPARTY_DIR."/jquery/jquery.js");
0 ignored issues
show
Unused Code Comprehensibility introduced by
56% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
88
        //Requirements::javascript(Director::protocol()."ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js");
0 ignored issues
show
Unused Code Comprehensibility introduced by
62% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
89
        //todo: check if we even need this (via ShoppingCartsRequirements.ss)
90
        if ($this->owner->dataRecord) {
91
            if (is_a($this->owner->dataRecord, Object::getCustomClass('Product')) || is_a($this->owner->dataRecord, Object::getCustomClass('ProductGroup'))) {
92
                Session::set('ContinueShoppingLink', $this->owner->Link());
93
            }
94
        }
95
    }
96
97
    /**
98
     * Standard SS method.
99
     * Runs after the Page::init method is called.
100
     */
101
    public function onAfterInit()
102
    {
103
        Requirements::javascript(EcommerceConfig::get('EcommerceConfigAjax', 'cart_js_file_location'));
104
        Requirements::javascript(EcommerceConfig::get('EcommerceConfigAjax', 'dialogue_js_file_location'));
105
        Requirements::themedCSS('Cart', 'ecommerce');
106
        Requirements::themedCSS('jquery.colorbox', 'ecommerce');
107
    }
108
109
    /**
110
     * This returns a link that displays just the cart, for use in ajax calls.
111
     *
112
     * @see ShoppingCart::showcart
113
     * It uses AjaxSimpleCart.ss to render the cart.
114
     *
115
     * @return string
116
     **/
117
    public function SimpleCartLinkAjax()
118
    {
119
        return EcommerceConfig::get('ShoppingCart_Controller', 'url_segment').'/showcart/?ajax=1';
120
    }
121
122
    /**
123
     * returns the current order.
124
     *
125
     * @return Order
126
     **/
127
    public function Cart()
128
    {
129
        return ShoppingCart::current_order();
130
    }
131
132
    /**
133
     * @return string (Link)
134
     */
135
    public function ContinueShoppingLink()
136
    {
137
        $link = Session::get('ContinueShoppingLink');
138
        if (!$link) {
139
            $link = Director::baseURL();
140
        }
141
142
        return $link;
143
    }
144
145
146
    /**
147
     * Is the page a secure page?
148
     *
149
     * @return true/false
0 ignored issues
show
Documentation introduced by
The doc-type true/false could not be parsed: Unknown type name "true/false" 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...
150
     */
151
    public function isSecurePage()
152
    {
153
        return $this->owner->dataRecord instanceof CartPage;
154
    }
155
156
    /**
157
     * Redirect users if found on incorrect domain
158
     * Detects if $_GET['session'] is present, sets session
159
     * and redirects back to "clean URL"
160
     * Both _SECURE_URL and _STANDARD_URL must be defined,
161
     * and include protocol (http(s)://mydomain.com) with no trailing slash.
162
    *    protected function secureHostSwitcher()
163
    *     {
164
    *    if (!DEFINED('_SECURE_URL') || !DEFINED('_STANDARD_URL')) {
165
    *        return false;
166
    *    }
167
    *
168
    *    $protocol = Director::is_https() ? 'https://' : 'http://';
169
    *    $currentUrlFull = $protocol.$_SERVER['HTTP_HOST'].$_SERVER['REQUEST_URI'];
170
    *    list($currentUrlFull) = explode('#', $currentUrlFull);
171
    *    $currentUrlWithoutHost = $_SERVER['REQUEST_URI'];
172
    *    //remove fragment...just to keep it simple...
173
    *    list($currentUrlWithoutHost) = explode('#', $currentUrlWithoutHost);
174
    *    $sessionPartOfURL = '';
175
    *    $sessionID = session_id();
176
    *    if ($sessionID) {
177
    *        if (strpos($currentUrlWithoutHost, '?')) {
178
    *            $sessionPartOfURL .= '&';
179
    *        } else {
180
    *            $sessionPartOfURL = '?';
181
    *        }
182
    *        $sessionPartOfURL .= 'session='.$sessionID;
183
    *        $currentUrlWithoutHost .= $sessionPartOfURL;
184
    *    }
185
    *
186
    *        $isSecure = $this->owner->isSecurePage();
187
    *
188
    *    if ($isSecure && !preg_match('/^'.preg_quote(_SECURE_URL, '/').'/', $currentUrlFull)) {
189
    *        return $this->owner->redirect(_SECURE_URL.$currentUrlWithoutHost);
190
    *    } elseif (!$isSecure && !preg_match('/^'.preg_quote(_STANDARD_URL, '/').'/', $currentUrlFull)) {
191
    *        return $this->owner->redirect(_STANDARD_URL.$currentUrlWithoutHost);
192
    *    }
193
    *
194
    *    if ($sessionID = $this->owner->request->getVar('session')) {
195
    *        $currentUrlFull = str_replace('?session='.$sessionID, '', $currentUrlFull);
196
    *        $currentUrlFull = str_replace('&session='.$sessionID, '', $currentUrlFull);
197
    *        // force hard-coded session setting
198
    *        @session_write_close();
199
    *        @session_id($sessionID);
200
    *        @session_start();
201
    *        header('location: '.$currentUrlFull, 302);
202
    *        exit;
203
    *    }
204
    *}
205
    */
206
}
207