Compare commits

...

7 commits
0.4.1 ... main

Author SHA1 Message Date
2cbb64dede
fixie privacy
All checks were successful
/ ls (pull_request) Successful in 1m33s
/ ls (push) Successful in 1m31s
2025-06-28 21:26:37 +02:00
4d2ae3a6ab #98 make background more bonkers
All checks were successful
/ ls (pull_request) Successful in 1m33s
/ ls (release) Successful in 1m1s
/ ls (push) Successful in 1m31s
2025-06-21 13:35:30 +00:00
98feafa3fc
ammend
All checks were successful
/ ls (pull_request) Successful in 1m35s
/ ls (push) Successful in 1m31s
2025-06-21 15:20:08 +02:00
c8e6af6896
#97: add emojis to foodvendor 2025-06-21 15:15:47 +02:00
e2167fa19f
haaaah
Some checks failed
/ ls (pull_request) Failing after 22s
/ ls (release) Successful in 57s
/ ls (push) Successful in 1m29s
2025-06-18 20:54:19 +02:00
c29e09ccc0
hmmmmm
Some checks failed
/ ls (pull_request) Failing after 23s
/ ls (push) Successful in 1m29s
/ ls (release) Successful in 59s
2025-06-18 20:47:13 +02:00
a5e54e9f5b
lol;
Some checks failed
/ ls (pull_request) Failing after 23s
/ ls (release) Successful in 55s
/ ls (push) Successful in 1m31s
2025-06-18 20:26:48 +02:00
17 changed files with 618 additions and 21 deletions

View file

@ -14,9 +14,11 @@ import './javascript/theme.js';
import './javascript/emoji-footprint.js'; import './javascript/emoji-footprint.js';
import './javascript/modes.js'; import './javascript/modes.js';
import './javascript/htmx.js'; import './javascript/htmx.js';
import emojiButtonListener from './javascript/emoji-button.js';
import 'bootstrap'; import 'bootstrap';
import { initRadioState } from './javascript/radioState.js'; import { initRadioState } from './javascript/radioState.js';
document.addEventListener('DOMContentLoaded', () => { document.addEventListener('DOMContentLoaded', () => {
initRadioState(); initRadioState();
emojiButtonListener();
}); });

View file

@ -0,0 +1,14 @@
const emojiButtonListener = function () {
const buttons = document.querySelectorAll('.emoji-buttons .btn.btn-primary');
buttons.forEach(button => {
button.addEventListener('click', function() {
const emojiField = document.querySelector('#food_vendor_emojis');
if (emojiField) {
emojiField.value += this.textContent;
}
});
});
}
export default emojiButtonListener;

View file

@ -86,6 +86,9 @@
/* 🎭 BONKERS MODE CLASSES 🎭 */ /* 🎭 BONKERS MODE CLASSES 🎭 */
.bonkers-mode { .bonkers-mode {
background: linear-gradient(270deg, var(--bs-pink), var(--bs-purple), var(--bs-cyan), var(--bs-yellow), var(--bs-green), var(--bs-orange), var(--bs-red), var(--bs-pink));
background-size: 1600% 1600%;
animation: rainbowGradient 10s ease infinite;
transition: all 0.3s ease-in-out; transition: all 0.3s ease-in-out;
} }

View file

@ -25,6 +25,7 @@
"symfony/flex": "^2.7.1", "symfony/flex": "^2.7.1",
"symfony/form": "7.3.*", "symfony/form": "7.3.*",
"symfony/framework-bundle": "7.3.*", "symfony/framework-bundle": "7.3.*",
"symfony/monolog-bundle": "^3.10",
"symfony/property-access": "7.3.*", "symfony/property-access": "7.3.*",
"symfony/property-info": "7.3.*", "symfony/property-info": "7.3.*",
"symfony/runtime": "7.3.*", "symfony/runtime": "7.3.*",

268
composer.lock generated
View file

@ -4,7 +4,7 @@
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically" "This file is @generated automatically"
], ],
"content-hash": "f7f3513731749141a755b5e676088c7d", "content-hash": "923bae46e3b7f783b6c25f8f68f97991",
"packages": [ "packages": [
{ {
"name": "api-platform/core", "name": "api-platform/core",
@ -1422,6 +1422,109 @@
}, },
"time": "2025-01-24T11:45:48+00:00" "time": "2025-01-24T11:45:48+00:00"
}, },
{
"name": "monolog/monolog",
"version": "3.9.0",
"source": {
"type": "git",
"url": "https://github.com/Seldaek/monolog.git",
"reference": "10d85740180ecba7896c87e06a166e0c95a0e3b6"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/Seldaek/monolog/zipball/10d85740180ecba7896c87e06a166e0c95a0e3b6",
"reference": "10d85740180ecba7896c87e06a166e0c95a0e3b6",
"shasum": ""
},
"require": {
"php": ">=8.1",
"psr/log": "^2.0 || ^3.0"
},
"provide": {
"psr/log-implementation": "3.0.0"
},
"require-dev": {
"aws/aws-sdk-php": "^3.0",
"doctrine/couchdb": "~1.0@dev",
"elasticsearch/elasticsearch": "^7 || ^8",
"ext-json": "*",
"graylog2/gelf-php": "^1.4.2 || ^2.0",
"guzzlehttp/guzzle": "^7.4.5",
"guzzlehttp/psr7": "^2.2",
"mongodb/mongodb": "^1.8",
"php-amqplib/php-amqplib": "~2.4 || ^3",
"php-console/php-console": "^3.1.8",
"phpstan/phpstan": "^2",
"phpstan/phpstan-deprecation-rules": "^2",
"phpstan/phpstan-strict-rules": "^2",
"phpunit/phpunit": "^10.5.17 || ^11.0.7",
"predis/predis": "^1.1 || ^2",
"rollbar/rollbar": "^4.0",
"ruflin/elastica": "^7 || ^8",
"symfony/mailer": "^5.4 || ^6",
"symfony/mime": "^5.4 || ^6"
},
"suggest": {
"aws/aws-sdk-php": "Allow sending log messages to AWS services like DynamoDB",
"doctrine/couchdb": "Allow sending log messages to a CouchDB server",
"elasticsearch/elasticsearch": "Allow sending log messages to an Elasticsearch server via official client",
"ext-amqp": "Allow sending log messages to an AMQP server (1.0+ required)",
"ext-curl": "Required to send log messages using the IFTTTHandler, the LogglyHandler, the SendGridHandler, the SlackWebhookHandler or the TelegramBotHandler",
"ext-mbstring": "Allow to work properly with unicode symbols",
"ext-mongodb": "Allow sending log messages to a MongoDB server (via driver)",
"ext-openssl": "Required to send log messages using SSL",
"ext-sockets": "Allow sending log messages to a Syslog server (via UDP driver)",
"graylog2/gelf-php": "Allow sending log messages to a GrayLog2 server",
"mongodb/mongodb": "Allow sending log messages to a MongoDB server (via library)",
"php-amqplib/php-amqplib": "Allow sending log messages to an AMQP server using php-amqplib",
"rollbar/rollbar": "Allow sending log messages to Rollbar",
"ruflin/elastica": "Allow sending log messages to an Elastic Search server"
},
"type": "library",
"extra": {
"branch-alias": {
"dev-main": "3.x-dev"
}
},
"autoload": {
"psr-4": {
"Monolog\\": "src/Monolog"
}
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "Jordi Boggiano",
"email": "j.boggiano@seld.be",
"homepage": "https://seld.be"
}
],
"description": "Sends your logs to files, sockets, inboxes, databases and various web services",
"homepage": "https://github.com/Seldaek/monolog",
"keywords": [
"log",
"logging",
"psr-3"
],
"support": {
"issues": "https://github.com/Seldaek/monolog/issues",
"source": "https://github.com/Seldaek/monolog/tree/3.9.0"
},
"funding": [
{
"url": "https://github.com/Seldaek",
"type": "github"
},
{
"url": "https://tidelift.com/funding/github/packagist/monolog/monolog",
"type": "tidelift"
}
],
"time": "2025-03-24T10:02:05+00:00"
},
{ {
"name": "nelmio/cors-bundle", "name": "nelmio/cors-bundle",
"version": "2.5.0", "version": "2.5.0",
@ -4020,6 +4123,165 @@
], ],
"time": "2025-05-29T07:47:32+00:00" "time": "2025-05-29T07:47:32+00:00"
}, },
{
"name": "symfony/monolog-bridge",
"version": "v7.3.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/monolog-bridge.git",
"reference": "1b188c8abbbef25b111da878797514b7a8d33990"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/monolog-bridge/zipball/1b188c8abbbef25b111da878797514b7a8d33990",
"reference": "1b188c8abbbef25b111da878797514b7a8d33990",
"shasum": ""
},
"require": {
"monolog/monolog": "^3",
"php": ">=8.2",
"symfony/http-kernel": "^6.4|^7.0",
"symfony/service-contracts": "^2.5|^3"
},
"conflict": {
"symfony/console": "<6.4",
"symfony/http-foundation": "<6.4",
"symfony/security-core": "<6.4"
},
"require-dev": {
"symfony/console": "^6.4|^7.0",
"symfony/http-client": "^6.4|^7.0",
"symfony/mailer": "^6.4|^7.0",
"symfony/messenger": "^6.4|^7.0",
"symfony/mime": "^6.4|^7.0",
"symfony/security-core": "^6.4|^7.0",
"symfony/var-dumper": "^6.4|^7.0"
},
"type": "symfony-bridge",
"autoload": {
"psr-4": {
"Symfony\\Bridge\\Monolog\\": ""
},
"exclude-from-classmap": [
"/Tests/"
]
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "Fabien Potencier",
"email": "fabien@symfony.com"
},
{
"name": "Symfony Community",
"homepage": "https://symfony.com/contributors"
}
],
"description": "Provides integration for Monolog with various Symfony components",
"homepage": "https://symfony.com",
"support": {
"source": "https://github.com/symfony/monolog-bridge/tree/v7.3.0"
},
"funding": [
{
"url": "https://symfony.com/sponsor",
"type": "custom"
},
{
"url": "https://github.com/fabpot",
"type": "github"
},
{
"url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
"type": "tidelift"
}
],
"time": "2025-03-21T12:17:46+00:00"
},
{
"name": "symfony/monolog-bundle",
"version": "v3.10.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/monolog-bundle.git",
"reference": "414f951743f4aa1fd0f5bf6a0e9c16af3fe7f181"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/monolog-bundle/zipball/414f951743f4aa1fd0f5bf6a0e9c16af3fe7f181",
"reference": "414f951743f4aa1fd0f5bf6a0e9c16af3fe7f181",
"shasum": ""
},
"require": {
"monolog/monolog": "^1.25.1 || ^2.0 || ^3.0",
"php": ">=7.2.5",
"symfony/config": "^5.4 || ^6.0 || ^7.0",
"symfony/dependency-injection": "^5.4 || ^6.0 || ^7.0",
"symfony/http-kernel": "^5.4 || ^6.0 || ^7.0",
"symfony/monolog-bridge": "^5.4 || ^6.0 || ^7.0"
},
"require-dev": {
"symfony/console": "^5.4 || ^6.0 || ^7.0",
"symfony/phpunit-bridge": "^6.3 || ^7.0",
"symfony/yaml": "^5.4 || ^6.0 || ^7.0"
},
"type": "symfony-bundle",
"extra": {
"branch-alias": {
"dev-master": "3.x-dev"
}
},
"autoload": {
"psr-4": {
"Symfony\\Bundle\\MonologBundle\\": ""
},
"exclude-from-classmap": [
"/Tests/"
]
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"authors": [
{
"name": "Fabien Potencier",
"email": "fabien@symfony.com"
},
{
"name": "Symfony Community",
"homepage": "https://symfony.com/contributors"
}
],
"description": "Symfony MonologBundle",
"homepage": "https://symfony.com",
"keywords": [
"log",
"logging"
],
"support": {
"issues": "https://github.com/symfony/monolog-bundle/issues",
"source": "https://github.com/symfony/monolog-bundle/tree/v3.10.0"
},
"funding": [
{
"url": "https://symfony.com/sponsor",
"type": "custom"
},
{
"url": "https://github.com/fabpot",
"type": "github"
},
{
"url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
"type": "tidelift"
}
],
"time": "2023-11-06T17:08:13+00:00"
},
{ {
"name": "symfony/options-resolver", "name": "symfony/options-resolver",
"version": "v7.3.0", "version": "v7.3.0",
@ -10519,7 +10781,7 @@
], ],
"aliases": [], "aliases": [],
"minimum-stability": "stable", "minimum-stability": "stable",
"stability-flags": [], "stability-flags": {},
"prefer-stable": true, "prefer-stable": true,
"prefer-lowest": false, "prefer-lowest": false,
"platform": { "platform": {
@ -10527,7 +10789,7 @@
"ext-ctype": "*", "ext-ctype": "*",
"ext-iconv": "*" "ext-iconv": "*"
}, },
"platform-dev": [], "platform-dev": {},
"platform-overrides": { "platform-overrides": {
"php": "8.4" "php": "8.4"
}, },

View file

@ -8,6 +8,7 @@ use Liip\TestFixturesBundle\LiipTestFixturesBundle;
use Nelmio\CorsBundle\NelmioCorsBundle; use Nelmio\CorsBundle\NelmioCorsBundle;
use Symfony\Bundle\FrameworkBundle\FrameworkBundle; use Symfony\Bundle\FrameworkBundle\FrameworkBundle;
use Symfony\Bundle\MakerBundle\MakerBundle; use Symfony\Bundle\MakerBundle\MakerBundle;
use Symfony\Bundle\MonologBundle\MonologBundle;
use Symfony\Bundle\SecurityBundle\SecurityBundle; use Symfony\Bundle\SecurityBundle\SecurityBundle;
use Symfony\Bundle\TwigBundle\TwigBundle; use Symfony\Bundle\TwigBundle\TwigBundle;
use Symfony\Bundle\WebProfilerBundle\WebProfilerBundle; use Symfony\Bundle\WebProfilerBundle\WebProfilerBundle;
@ -53,4 +54,7 @@ return [
TwigExtraBundle::class => [ TwigExtraBundle::class => [
'all' => true, 'all' => true,
], ],
MonologBundle::class => [
'all' => true,
],
]; ];

View file

@ -1,21 +1,19 @@
<?php declare(strict_types=1); <?php declare(strict_types=1);
use Symfony\Component\DependencyInjection\Loader\Configurator\ContainerConfigurator; use Symfony\Component\DependencyInjection\Loader\Configurator\ContainerConfigurator;
use Symfony\Config\FrameworkConfig;
return static function (ContainerConfigurator $containerConfigurator): void { return static function (
$containerConfigurator->extension('framework', [ ContainerConfigurator $containerConfigurator,
'asset_mapper' => [ FrameworkConfig $frameworkConfig,
'paths' => [ ): void {
'assets/', $frameworkConfig->assetMapper()
], ->path('assets/', true)
'missing_import_mode' => 'strict', ->missingImportMode('strict')
], ->importmapPolyfill(false)
]); ;
if ($containerConfigurator->env() === 'prod') { if ($containerConfigurator->env() === 'prod') {
$containerConfigurator->extension('framework', [ $frameworkConfig->assetMapper()
'asset_mapper' => [ ->missingImportMode('warn');
'missing_import_mode' => 'warn',
],
]);
} }
}; };

View file

@ -0,0 +1,95 @@
<?php declare(strict_types=1);
use Symfony\Component\DependencyInjection\Loader\Configurator\ContainerConfigurator;
return static function (ContainerConfigurator $containerConfigurator): void {
$containerConfigurator->extension('monolog', [
'channels' => [
'deprecation',
],
]);
if ($containerConfigurator->env() === 'dev') {
$containerConfigurator->extension('monolog', [
'handlers' => [
'main' => [
'type' => 'stream',
'path' => '%kernel.logs_dir%/%kernel.environment%.log',
'level' => 'debug',
'channels' => [
'!event',
],
],
'console' => [
'type' => 'console',
'process_psr_3_messages' => false,
'channels' => [
'!event',
'!doctrine',
'!console',
],
],
],
]);
}
if ($containerConfigurator->env() === 'test') {
$containerConfigurator->extension('monolog', [
'handlers' => [
'main' => [
'type' => 'fingers_crossed',
'action_level' => 'error',
'handler' => 'nested',
'excluded_http_codes' => [
404,
405,
],
'channels' => [
'!event',
],
],
'nested' => [
'type' => 'stream',
'path' => '%kernel.logs_dir%/%kernel.environment%.log',
'level' => 'debug',
],
],
]);
}
if ($containerConfigurator->env() === 'prod') {
$containerConfigurator->extension('monolog', [
'handlers' => [
'main' => [
'type' => 'fingers_crossed',
'action_level' => 'error',
'handler' => 'nested',
'excluded_http_codes' => [
404,
405,
],
'buffer_size' => 50,
],
'nested' => [
'type' => 'stream',
'path' => 'php://stderr',
'level' => 'debug',
'formatter' => 'monolog.formatter.json',
],
'console' => [
'type' => 'console',
'process_psr_3_messages' => false,
'channels' => [
'!event',
'!doctrine',
],
],
'deprecation' => [
'type' => 'stream',
'channels' => [
'deprecation',
],
'path' => 'php://stderr',
'formatter' => 'monolog.formatter.json',
],
],
]);
}
};

View file

@ -8,7 +8,7 @@ fi
mkdir $TARGETDIR mkdir $TARGETDIR
cd $TARGETDIR || return cd $TARGETDIR || return
pathsToCopy="public bin config migrations src templates composer.json composer.lock symfony.lock .env" pathsToCopy="assets public bin config migrations src templates composer.json composer.lock symfony.lock .env importmap.php"
for path in $pathsToCopy for path in $pathsToCopy
do do

View file

@ -5,4 +5,7 @@ systemctl --user start pod-futtern
sleep 2 sleep 2
podman exec -it futtern-php /var/www/html/bin/console cache:clear podman exec -it futtern-php /var/www/html/bin/console cache:clear
podman exec -it futtern-php /var/www/html/bin/console cache:warmup podman exec -it futtern-php /var/www/html/bin/console cache:warmup
podman exec -it futtern-php /var/www/html/bin/console asset-map:compile
echo 'yes' | podman exec -it futtern-php /var/www/html/bin/console doctrine:migrations:migrate echo 'yes' | podman exec -it futtern-php /var/www/html/bin/console doctrine:migrations:migrate

View file

@ -27,6 +27,6 @@ return [
'type' => 'css', 'type' => 'css',
], ],
'htmx.org' => [ 'htmx.org' => [
'version' => '1.9.12', 'version' => '2.0.5',
], ],
]; ];

View file

@ -0,0 +1,47 @@
<?php
declare(strict_types=1);
namespace DoctrineMigrations;
use Doctrine\DBAL\Schema\Schema;
use Doctrine\Migrations\AbstractMigration;
/**
* Auto-generated Migration: Please modify to your needs!
*/
final class Version20250621131822 extends AbstractMigration
{
public function getDescription(): string
{
return '';
}
public function up(Schema $schema): void
{
// this up() migration is auto-generated, please modify it to your needs
$this->addSql(<<<'SQL'
ALTER TABLE food_vendor ADD COLUMN emojis VARCHAR(30) DEFAULT NULL
SQL);
}
public function down(Schema $schema): void
{
// this down() migration is auto-generated, please modify it to your needs
$this->addSql(<<<'SQL'
CREATE TEMPORARY TABLE __temp__food_vendor AS SELECT name, phone, menu_link, id FROM food_vendor
SQL);
$this->addSql(<<<'SQL'
DROP TABLE food_vendor
SQL);
$this->addSql(<<<'SQL'
CREATE TABLE food_vendor (name VARCHAR(50) NOT NULL, phone VARCHAR(50) DEFAULT '', menu_link VARCHAR(255) DEFAULT NULL, id BLOB NOT NULL, PRIMARY KEY(id))
SQL);
$this->addSql(<<<'SQL'
INSERT INTO food_vendor (name, phone, menu_link, id) SELECT name, phone, menu_link, id FROM __temp__food_vendor
SQL);
$this->addSql(<<<'SQL'
DROP TABLE __temp__food_vendor
SQL);
}
}

View file

@ -7,23 +7,27 @@ use App\Repository\FoodVendorRepository;
use Doctrine\Common\Collections\ArrayCollection; use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\Common\Collections\Collection; use Doctrine\Common\Collections\Collection;
use Doctrine\ORM\Mapping as ORM; use Doctrine\ORM\Mapping as ORM;
use InvalidArgumentException;
use Symfony\Bridge\Doctrine\IdGenerator\UlidGenerator; use Symfony\Bridge\Doctrine\IdGenerator\UlidGenerator;
use Symfony\Bridge\Doctrine\Types\UlidType; use Symfony\Bridge\Doctrine\Types\UlidType;
use Symfony\Component\Serializer\Annotation\Groups; use Symfony\Component\Serializer\Annotation\Groups;
use Symfony\Component\Uid\Ulid; use Symfony\Component\Uid\Ulid;
use Symfony\Component\Validator\Constraints\Length;
use function mb_strlen;
#[ORM\Entity(repositoryClass: FoodVendorRepository::class)] #[ORM\Entity(repositoryClass: FoodVendorRepository::class)]
#[ApiResource] #[ApiResource]
class FoodVendor class FoodVendor
{ {
#[ORM\Column(length: 50)] #[ORM\Column(length: 50)]
#[Groups(['food_order:latest'])] #[Groups(['food_order:latest', 'food_vendor:read'])]
private string|null $name = null; private string|null $name = null;
#[ORM\Column(length: 50, nullable: true, options: [ #[ORM\Column(length: 50, nullable: true, options: [
'default' => '', 'default' => '',
])] ])]
#[Groups(['food_order:latest'])] #[Groups(['food_order:latest', 'food_vendor:read'])]
private string|null $phone = null; private string|null $phone = null;
/** /**
@ -42,6 +46,14 @@ class FoodVendor
#[Groups(['food_order:latest'])] #[Groups(['food_order:latest'])]
private string|null $menuLink = null; private string|null $menuLink = null;
/**
* String of emojis (max 30 characters)
*/
#[ORM\Column(length: 30, nullable: true)]
#[Groups(['food_order:latest', 'food_vendor:read'])]
#[Length(max: 10)]
private string|null $emojis = null;
public function __construct( public function __construct(
#[ORM\Id] #[ORM\Id]
#[ORM\GeneratedValue(strategy: 'CUSTOM')] #[ORM\GeneratedValue(strategy: 'CUSTOM')]
@ -155,4 +167,19 @@ class FoodVendor
$this->phone = $phone; $this->phone = $phone;
return $this; return $this;
} }
public function getEmojis(): string|null
{
return $this->emojis;
}
public function setEmojis(string|null $emojis): static
{
if ($emojis !== null && mb_strlen($emojis) > 30) {
throw new InvalidArgumentException('A maximum of 30 characters is allowed for emojis');
}
$this->emojis = $emojis;
return $this;
}
} }

View file

@ -17,6 +17,7 @@ final class FoodVendorType extends AbstractType
->add('name') ->add('name')
->add('menuLink') ->add('menuLink')
->add('phone') ->add('phone')
->add('emojis')
; ;
} }

View file

@ -196,6 +196,18 @@
"ref": "fadbfe33303a76e25cb63401050439aa9b1a9c7f" "ref": "fadbfe33303a76e25cb63401050439aa9b1a9c7f"
} }
}, },
"symfony/monolog-bundle": {
"version": "3.10",
"recipe": {
"repo": "github.com/symfony/recipes",
"branch": "main",
"version": "3.7",
"ref": "aff23899c4440dd995907613c1dd709b6f59503f"
},
"files": [
"config/packages/monolog.yaml"
]
},
"symfony/property-info": { "symfony/property-info": {
"version": "7.3", "version": "7.3",
"recipe": { "recipe": {

View file

@ -9,5 +9,121 @@
{{ include('food_vendor/_form.html.twig', {'button_label': 'Update'}) }} {{ include('food_vendor/_form.html.twig', {'button_label': 'Update'}) }}
</div> </div>
<div class="mb-4 emoji-buttons" data-role="emoji-selector">
<button class="btn btn-primary">🍕</button>
<button class="btn btn-primary">🍔</button>
<button class="btn btn-primary">🌮</button>
<button class="btn btn-primary">🍜</button>
<button class="btn btn-primary">🥗</button>
<button class="btn btn-primary">☕</button>
<button class="btn btn-primary">🍣</button>
<button class="btn btn-primary">🍤</button>
<button class="btn btn-primary">🍦</button>
<button class="btn btn-primary">🍩</button>
<button class="btn btn-primary">🍪</button>
<button class="btn btn-primary">🍰</button>
<button class="btn btn-primary">🍫</button>
<button class="btn btn-primary">🍿</button>
<button class="btn btn-primary">🍩</button>
<button class="btn btn-primary">🍭</button>
<button class="btn btn-primary">🍮</button>
<button class="btn btn-primary">🍯</button>
<button class="btn btn-primary">🍎</button>
<button class="btn btn-primary">🍊</button>
<button class="btn btn-primary">🍋</button>
<button class="btn btn-primary">🍌</button>
<button class="btn btn-primary">🍉</button>
<button class="btn btn-primary">🍇</button>
<button class="btn btn-primary">🍓</button>
<button class="btn btn-primary">🍈</button>
<button class="btn btn-primary">🍒</button>
<button class="btn btn-primary">🍍</button>
<button class="btn btn-primary">🥭</button>
<button class="btn btn-primary">🥥</button>
<button class="btn btn-primary">🥝</button>
<button class="btn btn-primary">🍅</button>
<button class="btn btn-primary">🍆</button>
<button class="btn btn-primary">🥑</button>
<button class="btn btn-primary">🥦</button>
<button class="btn btn-primary">🥒</button>
<button class="btn btn-primary">🌽</button>
<button class="btn btn-primary">🥕</button>
<button class="btn btn-primary">🧄</button>
<button class="btn btn-primary">🧅</button>
<button class="btn btn-primary">🥔</button>
<button class="btn btn-primary">🍠</button>
<button class="btn btn-primary">🥐</button>
<button class="btn btn-primary">🥯</button>
<button class="btn btn-primary">🍞</button>
<button class="btn btn-primary">🥖</button>
<button class="btn btn-primary">🥨</button>
<button class="btn btn-primary">🧀</button>
<button class="btn btn-primary">🥚</button>
<button class="btn btn-primary">🍳</button>
<button class="btn btn-primary">🥞</button>
<button class="btn btn-primary">🧇</button>
<button class="btn btn-primary">🥓</button>
<button class="btn btn-primary">🥩</button>
<button class="btn btn-primary">🍗</button>
<button class="btn btn-primary">🍖</button>
<button class="btn btn-primary">🌭</button>
<button class="btn btn-primary">🍔</button>
<button class="btn btn-primary">🍟</button>
<button class="btn btn-primary">🍕</button>
<button class="btn btn-primary">🥪</button>
<button class="btn btn-primary">🌮</button>
<button class="btn btn-primary">🌯</button>
<button class="btn btn-primary">🥙</button>
<button class="btn btn-primary">🧆</button>
<button class="btn btn-primary">🥘</button>
<button class="btn btn-primary">🍲</button>
<button class="btn btn-primary">🥣</button>
<button class="btn btn-primary">🥗</button>
<button class="btn btn-primary">🍿</button>
<button class="btn btn-primary">🧈</button>
<button class="btn btn-primary">🧂</button>
<button class="btn btn-primary">🥫</button>
<button class="btn btn-primary">🍱</button>
<button class="btn btn-primary">🍛</button>
<button class="btn btn-primary">🍚</button>
<button class="btn btn-primary">🍙</button>
<button class="btn btn-primary">🍘</button>
<button class="btn btn-primary">🍢</button>
<button class="btn btn-primary">🍡</button>
<button class="btn btn-primary">🍧</button>
<button class="btn btn-primary">🍨</button>
<button class="btn btn-primary">🍦</button>
<button class="btn btn-primary">🥧</button>
<button class="btn btn-primary">🍰</button>
<button class="btn btn-primary">🎂</button>
<button class="btn btn-primary">🍮</button>
<button class="btn btn-primary">🍭</button>
<button class="btn btn-primary">🍬</button>
<button class="btn btn-primary">🍫</button>
<button class="btn btn-primary">🍿</button>
<button class="btn btn-primary">🍩</button>
<button class="btn btn-primary">🍪</button>
<button class="btn btn-primary">🌰</button>
<button class="btn btn-primary">🥜</button>
<button class="btn btn-primary">🍯</button>
<button class="btn btn-primary">🥛</button>
<button class="btn btn-primary">🍼</button>
<button class="btn btn-primary">☕</button>
<button class="btn btn-primary">🍵</button>
<button class="btn btn-primary">🍶</button>
<button class="btn btn-primary">🍾</button>
<button class="btn btn-primary">🍷</button>
<button class="btn btn-primary">🍸</button>
<button class="btn btn-primary">🍹</button>
<button class="btn btn-primary">🍺</button>
<button class="btn btn-primary">🍻</button>
<button class="btn btn-primary">🥂</button>
<button class="btn btn-primary">🥃</button>
<button class="btn btn-primary">🥤</button>
<button class="btn btn-primary">🧃</button>
<button class="btn btn-primary">🧉</button>
<button class="btn btn-primary">🧊</button>
</div>
<a class="btn btn-secondary" href="{{ path('app_food_vendor_index') }}">back to list</a> <a class="btn btn-secondary" href="{{ path('app_food_vendor_index') }}">back to list</a>
{% endblock %} {% endblock %}

View file

@ -5,6 +5,7 @@ namespace App\Tests\Unit\Entity;
use App\Entity\FoodOrder; use App\Entity\FoodOrder;
use App\Entity\FoodVendor; use App\Entity\FoodVendor;
use App\Entity\MenuItem; use App\Entity\MenuItem;
use InvalidArgumentException;
use Symfony\Component\Uid\Ulid; use Symfony\Component\Uid\Ulid;
use function describe; use function describe;
@ -20,6 +21,17 @@ describe(FoodVendor::class, function (): void {
$vendor->setPhone('1234567890'); $vendor->setPhone('1234567890');
$this->assertEquals('1234567890', $vendor->getPhone()); $this->assertEquals('1234567890', $vendor->getPhone());
// Test emojis field
$this->assertNull($vendor->getEmojis());
$emojis = '😀😂🎉👍❤️';
$vendor->setEmojis($emojis);
$this->assertEquals($emojis, $vendor->getEmojis());
// Test emojis validation
$tooManyEmojis = '😀😂🎉👍❤️🚀🎈🎁🎊🎋🎍🎎🎏🎐🎑🎒🎓🎔🎕🎖🎗🎘🎙🎚🎛🎜🎝🎞🎟🎠🎡🎢';
$this->expectException(InvalidArgumentException::class);
$vendor->setEmojis($tooManyEmojis);
$this->assertCount(0, $vendor->getFoodOrders()); $this->assertCount(0, $vendor->getFoodOrders());
$order1 = new FoodOrder; $order1 = new FoodOrder;
$vendor->addFoodOrder($order1); $vendor->addFoodOrder($order1);