invoices: unified money, number and date formats and fully respect configured language (#1814)

This commit is contained in:
Kevin Papst
2020-07-10 15:09:52 +02:00
committed by GitHub
parent 19e4ebf88c
commit 32c1e3258e
67 changed files with 1593 additions and 2335 deletions

View File

@@ -0,0 +1,74 @@
<?php
/*
* This file is part of the Kimai time-tracking app.
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace App\Invoice\Renderer;
use App\Entity\InvoiceDocument;
use App\Invoice\InvoiceModel;
use App\Invoice\RendererInterface;
use App\Twig\DateExtensions;
use App\Twig\LocaleExtensions;
use Symfony\Bridge\Twig\Extension\TranslationExtension;
use Symfony\Contracts\Translation\LocaleAwareInterface;
use Twig\Environment;
/**
* @internal
*/
abstract class AbstractTwigRenderer implements RendererInterface
{
/**
* @var Environment
*/
private $twig;
public function __construct(Environment $twig)
{
$this->twig = $twig;
}
protected function renderTwigTemplate(InvoiceDocument $document, InvoiceModel $model): string
{
$previousLocale = $this->changeTwigLocale($this->twig, $model->getTemplate()->getLanguage());
$content = $this->twig->render('@invoice/' . basename($document->getFilename()), [
'model' => $model
]);
$this->changeTwigLocale($this->twig, $previousLocale);
return $content;
}
private function changeTwigLocale(Environment $twig, ?string $locale = null): ?string
{
// for invoices that don't have a language configured (using request locale)
if (null === $locale) {
return null;
}
/** @var TranslationExtension $extension */
$extension = $twig->getExtension(TranslationExtension::class);
/** @var LocaleAwareInterface $translator */
$translator = $extension->getTranslator();
$previousLocale = $translator->getLocale();
$translator->setLocale($locale);
/** @var LocaleExtensions $extension */
$extension = $twig->getExtension(LocaleExtensions::class);
$extension->setLocale($locale);
/** @var DateExtensions $extension */
$extension = $twig->getExtension(DateExtensions::class);
$extension->setLocale($locale);
return $previousLocale;
}
}

View File

@@ -12,23 +12,11 @@ namespace App\Invoice\Renderer;
use App\Entity\InvoiceDocument;
use App\Invoice\InvoiceFilename;
use App\Invoice\InvoiceModel;
use App\Invoice\RendererInterface;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpFoundation\ResponseHeaderBag;
use Twig\Environment;
final class JsonRenderer implements RendererInterface
final class JsonRenderer extends AbstractTwigRenderer
{
/**
* @var Environment
*/
private $twig;
public function __construct(Environment $twig)
{
$this->twig = $twig;
}
public function supports(InvoiceDocument $document): bool
{
return stripos($document->getFilename(), '.json.twig') !== false;
@@ -36,9 +24,7 @@ final class JsonRenderer implements RendererInterface
public function render(InvoiceDocument $document, InvoiceModel $model): Response
{
$content = $this->twig->render('@invoice/' . basename($document->getFilename()), [
'model' => $model
]);
$content = $this->renderTwigTemplate($document, $model);
$filename = (string) new InvoiceFilename($model);
$response = new Response($content);

View File

@@ -12,18 +12,13 @@ namespace App\Invoice\Renderer;
use App\Entity\InvoiceDocument;
use App\Invoice\InvoiceFilename;
use App\Invoice\InvoiceModel;
use App\Invoice\RendererInterface;
use App\Utils\HtmlToPdfConverter;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpFoundation\ResponseHeaderBag;
use Twig\Environment;
final class PdfRenderer implements RendererInterface
final class PdfRenderer extends AbstractTwigRenderer
{
/**
* @var Environment
*/
private $twig;
/**
* @var HtmlToPdfConverter
*/
@@ -31,7 +26,7 @@ final class PdfRenderer implements RendererInterface
public function __construct(Environment $twig, HtmlToPdfConverter $converter)
{
$this->twig = $twig;
parent::__construct($twig);
$this->converter = $converter;
}
@@ -42,9 +37,7 @@ final class PdfRenderer implements RendererInterface
public function render(InvoiceDocument $document, InvoiceModel $model): Response
{
$content = $this->twig->render('@invoice/' . basename($document->getFilename()), [
'model' => $model
]);
$content = $this->renderTwigTemplate($document, $model);
$content = $this->converter->convertToPdf($content, [
'setAutoTopMargin' => 'pad',

View File

@@ -12,23 +12,11 @@ namespace App\Invoice\Renderer;
use App\Entity\InvoiceDocument;
use App\Invoice\InvoiceFilename;
use App\Invoice\InvoiceModel;
use App\Invoice\RendererInterface;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpFoundation\ResponseHeaderBag;
use Twig\Environment;
final class TextRenderer implements RendererInterface
final class TextRenderer extends AbstractTwigRenderer
{
/**
* @var Environment
*/
private $twig;
public function __construct(Environment $twig)
{
$this->twig = $twig;
}
public function supports(InvoiceDocument $document): bool
{
return stripos($document->getFilename(), '.txt.twig') !== false;
@@ -36,9 +24,7 @@ final class TextRenderer implements RendererInterface
public function render(InvoiceDocument $document, InvoiceModel $model): Response
{
$content = $this->twig->render('@invoice/' . basename($document->getFilename()), [
'model' => $model
]);
$content = $this->renderTwigTemplate($document, $model);
$filename = (string) new InvoiceFilename($model);
$response = new Response($content);

View File

@@ -11,22 +11,10 @@ namespace App\Invoice\Renderer;
use App\Entity\InvoiceDocument;
use App\Invoice\InvoiceModel;
use App\Invoice\RendererInterface;
use Symfony\Component\HttpFoundation\Response;
use Twig\Environment;
final class TwigRenderer implements RendererInterface
final class TwigRenderer extends AbstractTwigRenderer
{
/**
* @var Environment
*/
private $twig;
public function __construct(Environment $twig)
{
$this->twig = $twig;
}
public function supports(InvoiceDocument $document): bool
{
return stripos($document->getFilename(), '.html.twig') !== false;
@@ -34,9 +22,7 @@ final class TwigRenderer implements RendererInterface
public function render(InvoiceDocument $document, InvoiceModel $model): Response
{
$content = $this->twig->render('@invoice/' . basename($document->getFilename()), [
'model' => $model
]);
$content = $this->renderTwigTemplate($document, $model);
$response = new Response();
$response->setContent($content);

View File

@@ -12,23 +12,11 @@ namespace App\Invoice\Renderer;
use App\Entity\InvoiceDocument;
use App\Invoice\InvoiceFilename;
use App\Invoice\InvoiceModel;
use App\Invoice\RendererInterface;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpFoundation\ResponseHeaderBag;
use Twig\Environment;
final class XmlRenderer implements RendererInterface
final class XmlRenderer extends AbstractTwigRenderer
{
/**
* @var Environment
*/
private $twig;
public function __construct(Environment $twig)
{
$this->twig = $twig;
}
public function supports(InvoiceDocument $document): bool
{
return stripos($document->getFilename(), '.xml.twig') !== false;
@@ -36,9 +24,7 @@ final class XmlRenderer implements RendererInterface
public function render(InvoiceDocument $document, InvoiceModel $model): Response
{
$content = $this->twig->render('@invoice/' . basename($document->getFilename()), [
'model' => $model
]);
$content = $this->renderTwigTemplate($document, $model);
$filename = (string) new InvoiceFilename($model);
$response = new Response($content);