Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit4663c22

Browse files
committed
[Workflow] Add a MetadataStore
1 parenta1b1a44 commit4663c22

File tree

26 files changed

+577
-72
lines changed

26 files changed

+577
-72
lines changed

‎UPGRADE-4.1.md‎

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -104,3 +104,13 @@ Workflow
104104
* Deprecated the `add` method in favor of the `addWorkflow` method in `Workflow\Registry`.
105105
* Deprecated `SupportStrategyInterface` in favor of `WorkflowSupportStrategyInterface`.
106106
* Deprecated the class `ClassInstanceSupportStrategy` in favor of the class `InstanceOfSupportStrategy`.
107+
* Deprecated passing the workflow name as 4th parameter of `Event` constructor in favor of the workflow itself.
108+
* You can now define a place in XML (support more feature such as metadata) like following:
109+
110+
before:
111+
112+
<framework:place>first</framework:place>
113+
114+
after:
115+
116+
<framework:place name="first" />

‎src/Symfony/Bridge/Twig/CHANGELOG.md‎

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,11 @@
11
CHANGELOG
22
=========
33

4+
4.1.0
5+
-----
6+
7+
* add a`workflow_metadata` function
8+
49
3.4.0
510
-----
611

‎src/Symfony/Bridge/Twig/Extension/WorkflowExtension.php‎

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@ public function getFunctions()
3737
newTwigFunction('workflow_transitions',array($this,'getEnabledTransitions')),
3838
newTwigFunction('workflow_has_marked_place',array($this,'hasMarkedPlace')),
3939
newTwigFunction('workflow_marked_places',array($this,'getMarkedPlaces')),
40+
newTwigFunction('workflow_metadata',array($this,'getMetadata')),
4041
);
4142
}
4243

@@ -101,6 +102,24 @@ public function getMarkedPlaces($subject, $placesNameOnly = true, $name = null)
101102
return$places;
102103
}
103104

105+
/**
106+
* Returns the metadata for a specific subject.
107+
*
108+
* @param object $subject A subject
109+
* @param null|string|Transition $metadataSubject Use null to get workflow metadata
110+
* Use a string (the place name) to get place metadata
111+
* Use a Transition instance to get transition metadata
112+
*/
113+
publicfunctiongetMetadata($subject,string$key,$metadataSubject =null,string$name =null): ?string
114+
{
115+
return$this
116+
->workflowRegistry
117+
->get($subject,$name)
118+
->getMetadataStore()
119+
->getMetadata($key,$metadataSubject)
120+
;
121+
}
122+
104123
publicfunctiongetName()
105124
{
106125
return'workflow';

‎src/Symfony/Bridge/Twig/Tests/Extension/WorkflowExtensionTest.php‎

Lines changed: 30 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
usePHPUnit\Framework\TestCase;
1515
useSymfony\Bridge\Twig\Extension\WorkflowExtension;
1616
useSymfony\Component\Workflow\Definition;
17+
useSymfony\Component\Workflow\Metadata\InMemoryMetadataStore;
1718
useSymfony\Component\Workflow\Registry;
1819
useSymfony\Component\Workflow\SupportStrategy\ClassInstanceSupportStrategy;
1920
useSymfony\Component\Workflow\SupportStrategy\InstanceOfSupportStrategy;
@@ -23,6 +24,7 @@
2324
class WorkflowExtensionTestextends TestCase
2425
{
2526
private$extension;
27+
private$t1;
2628

2729
protectedfunctionsetUp()
2830
{
@@ -32,10 +34,21 @@ protected function setUp()
3234

3335
$places =array('ordered','waiting_for_payment','processed');
3436
$transitions =array(
35-
newTransition('t1','ordered','waiting_for_payment'),
37+
$this->t1 =newTransition('t1','ordered','waiting_for_payment'),
3638
newTransition('t2','waiting_for_payment','processed'),
3739
);
38-
$definition =newDefinition($places,$transitions);
40+
41+
$metadataStore =null;
42+
if (class_exists(InMemoryMetadataStore::class)) {
43+
$transitionsMetadata =new \SplObjectStorage();
44+
$transitionsMetadata->attach($this->t1,array('title' =>'t1 title'));
45+
$metadataStore =newInMemoryMetadataStore(
46+
array('title' =>'workflow title'),
47+
array('orderer' =>array('title' =>'ordered title')),
48+
$transitionsMetadata
49+
);
50+
}
51+
$definition =newDefinition($places,$transitions,null,$metadataStore);
3952
$workflow =newWorkflow($definition);
4053

4154
$registry =newRegistry();
@@ -88,4 +101,19 @@ public function testGetMarkedPlaces()
88101
$this->assertSame(array('ordered','waiting_for_payment'),$this->extension->getMarkedPlaces($subject));
89102
$this->assertSame($subject->marking,$this->extension->getMarkedPlaces($subject,false));
90103
}
104+
105+
publicfunctiontestGetMetadata()
106+
{
107+
if (!class_exists(InMemoryMetadataStore::class)) {
108+
$this->markTestSkipped('This test requires symfony/workflow:4.1.');
109+
}
110+
$subject =new \stdClass();
111+
$subject->marking =array();
112+
113+
$this->assertSame('workflow title',$this->extension->getMetadata($subject,'title'));
114+
$this->assertSame('ordered title',$this->extension->getMetadata($subject,'title','orderer'));
115+
$this->assertSame('t1 title',$this->extension->getMetadata($subject,'title',$this->t1));
116+
$this->assertNull($this->extension->getMetadata($subject,'not found'));
117+
$this->assertNull($this->extension->getMetadata($subject,'not found',$this->t1));
118+
}
91119
}

‎src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Configuration.php‎

Lines changed: 57 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@
3131
* FrameworkExtension configuration structure.
3232
*
3333
* @author Jeremy Mikola <jmikola@gmail.com>
34+
* @author Grégoire Pineau <lyrixx@lyrixx.info>
3435
*/
3536
class Configurationimplements ConfigurationInterface
3637
{
@@ -292,23 +293,61 @@ private function addWorkflowSection(ArrayNodeDefinition $rootNode)
292293
->defaultNull()
293294
->end()
294295
->arrayNode('places')
296+
->beforeNormalization()
297+
->always()
298+
->then(function ($places) {
299+
// It's an indexed array of shape ['place1', 'place2']
300+
if (isset($places[0]) &&is_string($places[0])) {
301+
returnarray_map(function (string$place) {
302+
returnarray('name' =>$place);
303+
},$places);
304+
}
305+
306+
// It's an indexed array, we let the validation occurs
307+
if (isset($places[0]) &&is_array($places[0])) {
308+
return$places;
309+
}
310+
311+
foreach ($placesas$name =>$place) {
312+
if (is_array($place) &&array_key_exists('name',$place)) {
313+
continue;
314+
}
315+
$place['name'] =$name;
316+
$places[$name] =$place;
317+
}
318+
319+
returnarray_values($places);
320+
})
321+
->end()
295322
->isRequired()
296323
->requiresAtLeastOneElement()
297-
->prototype('scalar')
298-
->cannotBeEmpty()
324+
->prototype('array')
325+
->children()
326+
->scalarNode('name')
327+
->isRequired()
328+
->cannotBeEmpty()
329+
->end()
330+
->arrayNode('metadata')
331+
->normalizeKeys(false)
332+
->defaultValue(array())
333+
->example(array('color' =>'blue','description' =>'Workflow to manage article.'))
334+
->prototype('variable')
335+
->end()
336+
->end()
337+
->end()
299338
->end()
300339
->end()
301340
->arrayNode('transitions')
302341
->beforeNormalization()
303342
->always()
304343
->then(function ($transitions) {
305344
// It's an indexed array, we let the validation occurs
306-
if (isset($transitions[0])) {
345+
if (isset($transitions[0]) &&is_array($transitions[0])) {
307346
return$transitions;
308347
}
309348

310349
foreach ($transitionsas$name =>$transition) {
311-
if (array_key_exists('name',$transition)) {
350+
if (is_array($transition) &&array_key_exists('name',$transition)) {
312351
continue;
313352
}
314353
$transition['name'] =$name;
@@ -351,9 +390,23 @@ private function addWorkflowSection(ArrayNodeDefinition $rootNode)
351390
->cannotBeEmpty()
352391
->end()
353392
->end()
393+
->arrayNode('metadata')
394+
->normalizeKeys(false)
395+
->defaultValue(array())
396+
->example(array('color' =>'blue','description' =>'Workflow to manage article.'))
397+
->prototype('variable')
398+
->end()
399+
->end()
354400
->end()
355401
->end()
356402
->end()
403+
->arrayNode('metadata')
404+
->normalizeKeys(false)
405+
->defaultValue(array())
406+
->example(array('color' =>'blue','description' =>'Workflow to manage article.'))
407+
->prototype('variable')
408+
->end()
409+
->end()
357410
->end()
358411
->validate()
359412
->ifTrue(function ($v) {

‎src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php‎

Lines changed: 42 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -466,32 +466,68 @@ private function registerWorkflowConfiguration(array $config, ContainerBuilder $
466466
foreach ($config['workflows']as$name =>$workflow) {
467467
$type =$workflow['type'];
468468

469+
// Process Metadata (workflow + places (transition is done in the "create transition" block))
470+
$metadataStoreDefinition =newDefinition(Workflow\Metadata\InMemoryMetadataStore::class,array(null,null,null));
471+
if ($workflow['metadata']) {
472+
$metadataStoreDefinition->replaceArgument(0,$workflow['metadata']);
473+
}
474+
$placesMetadata =array();
475+
foreach ($workflow['places']as$place) {
476+
if ($place['metadata']) {
477+
$placesMetadata[$place['name']] =$place['metadata'];
478+
}
479+
}
480+
if ($placesMetadata) {
481+
$metadataStoreDefinition->replaceArgument(1,$placesMetadata);
482+
}
483+
484+
// Create transitions
469485
$transitions =array();
486+
$transitionsMetadataDefinition =newDefinition(\SplObjectStorage::class);
470487
foreach ($workflow['transitions']as$transition) {
471488
if ('workflow' ===$type) {
472-
$transitions[] =newDefinition(Workflow\Transition::class,array($transition['name'],$transition['from'],$transition['to']));
489+
$transitionDefinition =newDefinition(Workflow\Transition::class,array($transition['name'],$transition['from'],$transition['to']));
490+
$transitions[] =$transitionDefinition;
491+
if ($transition['metadata']) {
492+
$transitionsMetadataDefinition->addMethodCall('attach',array(
493+
$transitionDefinition,
494+
$transition['metadata'],
495+
));
496+
}
473497
}elseif ('state_machine' ===$type) {
474498
foreach ($transition['from']as$from) {
475499
foreach ($transition['to']as$to) {
476-
$transitions[] =newDefinition(Workflow\Transition::class,array($transition['name'],$from,$to));
500+
$transitionDefinition =newDefinition(Workflow\Transition::class,array($transition['name'],$from,$to));
501+
$transitions[] =$transitionDefinition;
502+
if ($transition['metadata']) {
503+
$transitionsMetadataDefinition->addMethodCall('attach',array(
504+
$transitionDefinition,
505+
$transition['metadata'],
506+
));
507+
}
477508
}
478509
}
479510
}
480511
}
512+
$metadataStoreDefinition->replaceArgument(2,$transitionsMetadataDefinition);
513+
514+
// Create places
515+
$places =array_map(function (array$place) {
516+
return$place['name'];
517+
},$workflow['places']);
481518

482519
// Create a Definition
483520
$definitionDefinition =newDefinition(Workflow\Definition::class);
484521
$definitionDefinition->setPublic(false);
485-
$definitionDefinition->addArgument($workflow['places']);
522+
$definitionDefinition->addArgument($places);
486523
$definitionDefinition->addArgument($transitions);
524+
$definitionDefinition->addArgument($workflow['initial_place'] ??null);
525+
$definitionDefinition->addArgument($metadataStoreDefinition);
487526
$definitionDefinition->addTag('workflow.definition',array(
488527
'name' =>$name,
489528
'type' =>$type,
490529
'marking_store' =>isset($workflow['marking_store']['type']) ?$workflow['marking_store']['type'] :null,
491530
));
492-
if (isset($workflow['initial_place'])) {
493-
$definitionDefinition->addArgument($workflow['initial_place']);
494-
}
495531

496532
// Create MarkingStore
497533
if (isset($workflow['marking_store']['type'])) {

‎src/Symfony/Bundle/FrameworkBundle/Resources/config/schema/symfony-1.0.xsd‎

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -273,8 +273,9 @@
273273
<xsd:sequence>
274274
<xsd:elementname="marking-store"type="marking_store"minOccurs="0"maxOccurs="1" />
275275
<xsd:elementname="support"type="xsd:string"minOccurs="0"maxOccurs="unbounded" />
276-
<xsd:elementname="place"type="xsd:string"minOccurs="0"maxOccurs="unbounded" />
276+
<xsd:elementname="place"type="place"minOccurs="0"maxOccurs="unbounded" />
277277
<xsd:elementname="transition"type="transition"minOccurs="0"maxOccurs="unbounded" />
278+
<xsd:elementname="metadata"type="metadata"minOccurs="0"maxOccurs="unbounded" />
278279
</xsd:sequence>
279280
<xsd:attributename="name"type="xsd:string" />
280281
<xsd:attributename="type"type="workflow_type" />
@@ -302,10 +303,24 @@
302303
<xsd:sequence>
303304
<xsd:elementname="from"type="xsd:string"minOccurs="1"maxOccurs="unbounded" />
304305
<xsd:elementname="to"type="xsd:string"minOccurs="1"maxOccurs="unbounded" />
306+
<xsd:elementname="metadata"type="metadata"minOccurs="0"maxOccurs="unbounded" />
305307
</xsd:sequence>
306308
<xsd:attributename="name"type="xsd:string"use="required" />
307309
</xsd:complexType>
308310

311+
<xsd:complexTypename="place"mixed="true">
312+
<xsd:sequence>
313+
<xsd:elementname="metadata"type="metadata"minOccurs="0"maxOccurs="unbounded" />
314+
</xsd:sequence>
315+
<xsd:attributename="name"type="xsd:string" />
316+
</xsd:complexType>
317+
318+
<xsd:complexTypename="metadata">
319+
<xsd:sequence>
320+
<xsd:anyminOccurs="0"processContents="lax"/>
321+
</xsd:sequence>
322+
</xsd:complexType>
323+
309324
<xsd:simpleTypename="workflow_type">
310325
<xsd:restrictionbase="xsd:string">
311326
<xsd:enumerationvalue="state_machine" />

‎src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/php/workflows.php‎

Lines changed: 19 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -48,18 +48,29 @@
4848
FrameworkExtensionTest::class,
4949
),
5050
'initial_place' =>'start',
51+
'metadata' =>array(
52+
'title' =>'workflow title',
53+
),
5154
'places' =>array(
52-
'start',
53-
'coding',
54-
'travis',
55-
'review',
56-
'merged',
57-
'closed',
55+
'start_name_not_used' =>array(
56+
'name' =>'start',
57+
'metadata' =>array(
58+
'title' =>'place start title',
59+
),
60+
),
61+
'coding' =>null,
62+
'travis' =>null,
63+
'review' =>null,
64+
'merged' =>null,
65+
'closed' =>null,
5866
),
5967
'transitions' =>array(
6068
'submit' =>array(
6169
'from' =>'start',
6270
'to' =>'travis',
71+
'metadata' =>array(
72+
'title' =>'transition submit title',
73+
),
6374
),
6475
'update' =>array(
6576
'from' =>array('coding','travis','review'),
@@ -96,8 +107,8 @@
96107
FrameworkExtensionTest::class,
97108
),
98109
'places' =>array(
99-
'first',
100-
'last',
110+
array('name' =>'first'),
111+
array('name' =>'last'),
101112
),
102113
'transitions' =>array(
103114
'go' =>array(

‎src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/Fixtures/xml/workflow_with_arguments_and_service.xml‎

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,8 +13,8 @@
1313
<framework:argument>a</framework:argument>
1414
</framework:marking-store>
1515
<framework:support>Symfony\Bundle\FrameworkBundle\Tests\DependencyInjection\FrameworkExtensionTest</framework:support>
16-
<framework:place>first</framework:place>
17-
<framework:place>last</framework:place>
16+
<framework:placename="first" />
17+
<framework:placename="last" />
1818
<framework:transitionname="foobar">
1919
<framework:from>a</framework:from>
2020
<framework:to>a</framework:to>

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp