# Pimcore

> Pimcore platform development - bundles, data objects, class definitions, CoreExtensions, events, workflows, documents, assets

- **Type:** Skill
- **Install:** `agentstack add skill-cors-gmbh-pimcore-skills-pimcore`
- **Verified:** Yes — security-reviewed for prompt injection and unsafe behavior
- **Seller:** [cors-gmbh](https://agentstack.voostack.com/s/cors-gmbh)
- **Installs:** 0
- **Category:** [Agent Skills](https://agentstack.voostack.com/c/agent-skills)
- **Latest version:** 0.1.0
- **License:** MIT
- **Upstream author:** [cors-gmbh](https://github.com/cors-gmbh)
- **Source:** https://github.com/cors-gmbh/pimcore-skills/tree/main/skills/pimcore

## Install

```sh
agentstack add skill-cors-gmbh-pimcore-skills-pimcore
```

Requires the [AgentStack CLI](https://agentstack.voostack.com/docs/cli). Works with Claude Code, Cursor, and any MCP-compatible agent.

## About

# Pimcore Platform Development

You are helping develop on the Pimcore platform. Before writing any code, load context about Pimcore's architecture and patterns.

## Step 1: Understand Pimcore's Three Pillars

Pimcore has three fundamental element types, all extending `Pimcore\Model\Element\AbstractElement`:

1. **Assets** — File management (images, videos, PDFs). Uses League Flysystem for storage.
2. **Documents** — Web pages, emails, links, snippets. Template-based rendering with editables.
3. **Data Objects** — Structured data (products, customers, etc.). Defined by Class Definitions.

Every element has: `id`, `path`, `key`, `creationDate`, `modificationDate`, `userOwner`, `properties`, `dependencies`.

## Step 2: Bundle Architecture

### AbstractPimcoreBundle
All Pimcore bundles extend `Pimcore\Extension\Bundle\AbstractPimcoreBundle` (not plain Symfony `Bundle`):

```php
use Pimcore\Extension\Bundle\AbstractPimcoreBundle;

class MyBundle extends AbstractPimcoreBundle
{
    public function getNiceName(): string { return 'My Bundle'; }
    public function getDescription(): string { return 'Description'; }
    public function getInstaller(): ?InstallerInterface { return $this->container->get(Installer::class); }
}
```

### DependencyInjection Pattern
```php
class MyBundleExtension extends ConfigurableExtension implements PrependExtensionInterface
{
    public function loadInternal(array $config, ContainerBuilder $container): void
    {
        $loader = new YamlFileLoader($container, new FileLocator(__DIR__.'/../config'));
        $loader->load('services.yaml');
    }
}
```

### Compiler Passes
Used heavily for tag collection, registry building, service decoration:
```php
public function build(ContainerBuilder $container): void
{
    parent::build($container);
    $container->addCompilerPass(new MyRegistryPass());
}
```

## Step 3: Data Object Class Definitions

Class Definitions define the structure of Data Objects (like database schemas).

### Field Types (`Pimcore\Model\DataObject\ClassDefinition\Data\*`)

**Basic**: `Input`, `Textarea`, `Wysiwyg`, `Numeric`, `Slider`, `Date`, `DateTime`, `Checkbox`, `Select`, `Multiselect`, `Email`, `Country`, `Language`

**Relations**: `ManyToOneRelation`, `ManyToManyRelation`, `AdvancedManyToManyRelation`

**Complex**: `Block` (repeating groups), `Fieldcollection`, `Localizedfields` (i18n), `ObjectBrick` (extendable), `Classificationstore` (dynamic attributes), `QuantityValue`

### Custom Field Types (CoreExtensions)
Add custom field types to the Class Definition editor:

```php
namespace MyBundle\CoreExtension;

use Pimcore\Model\DataObject\ClassDefinition\Data\Select;

class MyCustomField extends Select
{
    public string $fieldtype = 'myCustomField';

    public function getFieldType(): string {
        return $this->fieldtype;
    }
}
```

The `$fieldtype` string must match the frontend dynamic type ID exactly.

## Step 4: Event System

Pimcore uses Symfony EventDispatcher with predefined event constants:

```php
use Pimcore\Event\DataObjectEvents;
use Pimcore\Event\Model\DataObjectEvent;

class MySubscriber implements EventSubscriberInterface
{
    public static function getSubscribedEvents(): array
    {
        return [
            DataObjectEvents::POST_UPDATE => 'onPostUpdate',
            DataObjectEvents::PRE_DELETE => 'onPreDelete',
        ];
    }
}
```

**Event types per element**: `PRE_ADD`, `POST_ADD`, `PRE_UPDATE`, `POST_UPDATE`, `PRE_DELETE`, `POST_DELETE`, `POST_LOAD`, `PRE_COPY`, `POST_COPY`

**Event classes**: `AssetEvents`, `DataObjectEvents`, `DocumentEvents`

## Step 5: Workflow System

Built on Symfony Workflow Component, configured via YAML:

```yaml
pimcore:
    workflows:
        product_approval:
            enabled: true
            type: state_machine
            supports:
                - Pimcore\Model\DataObject\Product
            places: [draft, review, approved]
            transitions:
                submit_for_review:
                    from: draft
                    to: review
```

## Step 6: Pimcore Studio v2

The new admin UI is React/TypeScript with:
- **Backend**: `pimcore/studio-backend-bundle` — REST API (OpenAPI)
- **Frontend**: `pimcore/studio-ui-bundle` — React app with InversifyJS DI container
- **Real-time**: Symfony Mercure for live updates
- **Search**: `pimcore/generic-data-index-bundle`

### Plugin System
Studio plugins register via `IAbstractPlugin`:
```typescript
const plugin: IAbstractPlugin = {
  name: 'my-plugin',
  onInit() { /* DI bindings, dynamic types */ },
  onStartup({ moduleSystem }) { /* module/widget registration */ }
}
```

### Dynamic Types (Frontend)
Custom field types need frontend registration:
```typescript
import { DynamicTypeObjectDataAbstractSelect } from '@pimcore/studio-ui-bundle/modules/element'

export class DynamicTypeMyField extends DynamicTypeObjectDataAbstractSelect {
  readonly id = 'myCustomField' // Must match PHP $fieldtype
}
```

## Step 7: Configuration

Main config via `config/config.yaml`:
```yaml
pimcore:
    general:
        domain: "example.com"
    documents:
        default_controller: 'App\Controller\DefaultController::default'
    objects:
        class_definitions:
            data:
                map: {}
```

## Step 8: Caching

```php
use Pimcore\Cache;

// Core cache (Redis/Memcached/Filesystem)
Cache::save($data, 'my_key', ['tag1', 'tag2'], 3600);
Cache::load('my_key');
Cache::clearTag('tag1');

// In-memory runtime cache (current request only)
use Pimcore\Cache\RuntimeCache;
RuntimeCache::save('key', $data);
```

## Step 9: Installer Pattern

```php
use Pimcore\Extension\Bundle\Installer\AbstractInstaller;

class Installer extends AbstractInstaller
{
    public function install(): void { /* SQL migrations, permissions, configs */ }
    public function uninstall(): void { /* cleanup */ }
    public function isInstalled(): bool { /* check state */ }
}
```

## Step 10: Before Committing

- Validate YAML: `bin/console lint:yaml src`
- Validate Twig: `bin/console lint:twig src`
- Validate container: `bin/console lint:container`
- Clear cache: `bin/console cache:clear`

## Reference

See `.claude/skills/pimcore/reference.md` for directory structure templates and common patterns.

## Source & license

This open-source skill is cataloged on AgentStack and links to its original source — we do not rehost the code.

- **Author:** [cors-gmbh](https://github.com/cors-gmbh)
- **Source:** [cors-gmbh/pimcore-skills](https://github.com/cors-gmbh/pimcore-skills)
- **License:** MIT

Install and usage instructions live in the source repository linked above.

## Pricing

- **Free** — Free

## Security capabilities

Automated source analysis of v0.1.0 — what this tool can access:

- **Network access:** no
- **Filesystem access:** no
- **Shell / process execution:** no
- **Environment & secrets:** no
- **Dynamic code execution:** no

*"Yes" means the capability is present in the source — more access means more to trust, not that it is unsafe.*


## Versions

- **0.1.0** — security scan: passed — Imported from the upstream source.

## Links

- Listing page: https://agentstack.voostack.com/l/skill-cors-gmbh-pimcore-skills-pimcore
- Seller: https://agentstack.voostack.com/s/cors-gmbh
- Browse the marketplace: https://agentstack.voostack.com/browse

---
Listed on AgentStack — the marketplace for AI agent skills and MCP servers. Every listing is security-reviewed. Creators keep 70%.
