Completed
Push — develop ( a479cd...40bc58 )
by Wachter
14:35
created

WebsiteArticleController::renderBlock()   A

Complexity

Conditions 3
Paths 5

Size

Total Lines 24

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 12

Importance

Changes 0
Metric Value
dl 0
loc 24
ccs 0
cts 0
cp 0
rs 9.536
c 0
b 0
f 0
cc 3
nc 5
nop 3
crap 12
1
<?php
2
3
/*
4
 * This file is part of Sulu.
5
 *
6
 * (c) MASSIVE ART WebServices GmbH
7
 *
8
 * This source file is subject to the MIT license that is bundled
9
 * with this source code in the file LICENSE.
10
 */
11
12
namespace Sulu\Bundle\ArticleBundle\Controller;
13
14
use JMS\Serializer\SerializationContext;
15
use Sulu\Bundle\ArticleBundle\Document\ArticleDocument;
16
use Sulu\Bundle\ArticleBundle\Document\ArticleInterface;
17
use Sulu\Bundle\ArticleBundle\Document\ArticlePageDocument;
18
use Sulu\Bundle\HttpCacheBundle\Cache\SuluHttpCache;
19
use Sulu\Bundle\PreviewBundle\Preview\Preview;
20
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
21
use Symfony\Component\HttpFoundation\Request;
22
use Symfony\Component\HttpFoundation\Response;
23
use Symfony\Component\HttpKernel\Exception\HttpException;
24
25
/**
26
 * Handles articles.
27
 */
28
class WebsiteArticleController extends Controller
29
{
30
    /**
31
     * Article index action.
32
     *
33
     * @param Request $request
34
     * @param ArticleInterface $object
35
     * @param string $view
36
     * @param int $pageNumber
37
     *
38
     * @return Response
39
     */
40
    public function indexAction(Request $request, ArticleInterface $object, $view, $pageNumber = 1, $preview = false, $partial = false)
41
    {
42
        return $this->renderArticle($request, $object, $view, $pageNumber, $preview, $partial);
43
    }
44
45
    /**
46
     * Render article with given view.
47
     *
48
     * @param Request $request
49
     * @param ArticleInterface $object
50
     * @param string $view
51
     * @param int $pageNumber
52
     * @param array $attributes
53
     *
54
     * @return Response
55
     */
56
    protected function renderArticle(Request $request, ArticleInterface $object, $view, $pageNumber, $preview, $partial, $attributes = [])
57
    {
58
        $object = $this->normalizeArticle($object);
59
60
        $requestFormat = $request->getRequestFormat();
61
        $viewTemplate = $view . '.' . $requestFormat . '.twig';
62
63
        $content = $this->serializeArticle($object, $pageNumber);
64
65
        $data = $this->get('sulu_website.resolver.template_attribute')->resolve(array_merge($content, $attributes));
66
67
        try {
68
            if ($partial) {
69
                return new Response(
70
                    $this->renderBlock(
71
                        $viewTemplate,
72
                        'content',
73
                        $data
74
                    )
75
                );
76
            } else if ($preview) {
77
                $parameters = [
78
                    'previewParentTemplate' => $viewTemplate,
79
                    'previewContentReplacer' => Preview::CONTENT_REPLACER,
80
                ];
81
82
                return $this->render(
83
                    'SuluWebsiteBundle:Preview:preview.html.twig',
84
                    array_merge($data, $parameters),
85
                    $this->createResponse($request)
86
                );
87
            } else {
88
                return $this->render(
89
                    $viewTemplate,
90
                    $data,
91
                    $this->createResponse($request)
92
                );
93
            }
94
        } catch (\InvalidArgumentException $exception) {
95
            // template not found
96
            throw new HttpException(406, 'Error encountered when rendering content', $exception);
97
        }
98
    }
99
100
    /**
101
     * Returns all the times the article-document.
102
     * This is necessary because the preview system passes an article-page here.
103
     *
104
     * @param ArticleInterface $object
105
     *
106
     * @return ArticleDocument
107
     */
108
    protected function normalizeArticle(ArticleInterface $object)
109
    {
110
        if ($object instanceof ArticlePageDocument) {
111
            return $object->getParent();
112
        }
113
114
        return $object;
115
    }
116
117
    /**
118
     * Serialize given article with page-number.
119
     *
120
     * @param ArticleInterface $object
121
     * @param int $pageNumber
122
     *
123
     * @return array
124
     */
125
    protected function serializeArticle(ArticleInterface $object, $pageNumber)
126
    {
127
        return $this->get('jms_serializer')->serialize(
128
            $object,
129
            'array',
130
            SerializationContext::create()
131
                ->setSerializeNull(true)
132
                ->setGroups(['website', 'content'])
133
                ->setAttribute('website', true)
134
                ->setAttribute('pageNumber', $pageNumber)
135
        );
136
    }
137
138
    /**
139
     * Create response.
140
     *
141
     * @param Request $request
142
     *
143
     * @return Response
144
     */
145
    private function createResponse(Request $request)
146
    {
147
        $response = new Response();
148
        $cacheLifetime = $request->attributes->get('_cacheLifetime');
149
150
        if ($cacheLifetime) {
151
            $response->setPublic();
152
            $response->headers->set(
153
                SuluHttpCache::HEADER_REVERSE_PROXY_TTL,
154
                $cacheLifetime
155
            );
156
            $response->setMaxAge($this->getParameter('sulu_http_cache.cache.max_age'));
157
            $response->setSharedMaxAge($this->getParameter('sulu_http_cache.cache.shared_max_age'));
158
        }
159
160
        return $response;
161
    }
162
163
    protected function renderBlock($template, $block, $attributes = [])
164
    {
165
        $twig = $this->get('twig');
166
        $attributes = $twig->mergeGlobals($attributes);
167
168
        /** @var Template $template */
169
        $template = $twig->loadTemplate($template);
170
171
        $level = ob_get_level();
172
        ob_start();
173
174
        try {
175
            $rendered = $template->renderBlock($block, $attributes);
176
            ob_end_clean();
177
178
            return $rendered;
179
        } catch (\Exception $e) {
180
            while (ob_get_level() > $level) {
181
                ob_end_clean();
182
            }
183
184
            throw $e;
185
        }
186
    }
187
}
188