-
Notifications
You must be signed in to change notification settings - Fork 61
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
FEATURE: DataObject scaffolding #20
Merged
Merged
Changes from all commits
Commits
Show all changes
66 commits
Select commit
Hold shift + click to select a range
38535d8
FEATURE: DataObject scaffolding
ab44175
Fix phpunit.xml syntax
3b73495
README updates for scaffolding docs
81e0809
Remove @package declarations
51c0781
Change $dataObjectName to $dataObjectClass
a43d143
Type hinting
eaa4982
Updates to arg creation and resolver logic to all CRUD operations
68306e7
Add type detection to DataObject getters that are not casted
2c6379a
Remove @package declaration
5d061e7
Use new required resolver argument
ddb0781
More informative exception message
349cb17
New hasType() method for Manager
eb1ed99
Provide pagination in scaffolded queries
e353462
Cast default value for args
54de8f7
API changes to put queries and mutations at top level, nested query s…
a47421a
Remove creators, major reorganisation
327f60c
Update readme with new scaffolding api
cd2956c
Expose nested queries through public api
7cec89a
Move operation() method, allow removal by identifier
8068dd9
Allow allFieldsExcept to take a string
11c4c44
Move operation() method
7ccb104
Omit data object class from ancestry
ee2798a
Allow fieldsExcept or fields to be defined in config, not just fields
566623c
Bugfix: missing use statement
beafd24
Bugfix: missing use statement
11d4ce4
New public api, allowing find and remove by identifier
253065f
Change conditional block to not return too early
6e4d784
Change "scaffolds" to "types"
7a83af4
Use injector get instead of create
f5b0a38
Remove debug
b241d0d
Expose args to public api
fb5cd0d
Add new tests
554d5e8
format PSR2
d69a482
rename graphqlscaffolder to schemascaffolder
c4d9544
namespace updates to README
5f65e50
README updates
a823b20
Use non-matching group for type parser
28d8fd9
More README updates
a5dbd75
Add can* checks to examples
5ff2f6b
Add can* checks to CRUD using $context
69dbe7b
Add input type examples
5aa0310
replace member use statement
7daee8e
Add tests for CRUD operations
f6a3cc3
New addFields API, allow descriptions wildcard in yaml
46c1967
New argument API. Descriptions/defaults allowed
36302fe
Update example code
f49759c
BUGFIX: incorrect array shape for CRUD args
aeed6c7
BUGFIX: Malformed input type fields
4716387
PSR2 formatting
62cdf22
Code formatting for tests
d018593
Clean up rebasing issues
1066eb7
docblock revisions
7672e24
Rename Configurable to ConfigurationApplier
1977943
More docblock cleanup
d6eb733
Update example code to use DateTime
8296a23
Add new fake redirector page so tests pass without CMS
1456d5b
Build shim classes for Page, SiteTree
17dc73e
API Separate connection() to get/create
chillu c08bda7
Use DB transaction for multi delete
chillu 06ff0b2
Fix examples
chillu 198127c
Fix example $db declaration
chillu 641213b
Fix example whitespace
chillu 7047fba
Use DO->update() for create
chillu 3e981b7
Use DataObjectSchema
chillu 7d41007
More example class reference fixes
chillu fd5d41f
Correct use of currentUser context
chillu File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
Large diffs are not rendered by default.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
--- | ||
Name: graphqlconfig | ||
--- | ||
SilverStripe\GraphQL\Scaffolding\Scaffolders\DataObjectScaffolder: | ||
default_fields: | ||
ID: ID | ||
|
||
## Map DB fields to GraphQL types | ||
SilverStripe\ORM\FieldType\DBField: | ||
# fallback | ||
graphql_type: 'String' | ||
|
||
SilverStripe\ORM\FieldType\DBInt: | ||
graphql_type: 'Int' | ||
|
||
SilverStripe\ORM\FieldType\DBBoolean: | ||
graphql_type: 'Boolean' | ||
|
||
SilverStripe\ORM\FieldType\DBFloat: | ||
graphql_type: 'Float' | ||
|
||
SilverStripe\ORM\FieldType\DBPrimaryKey: | ||
graphql_type: 'ID' | ||
|
||
SilverStripe\ORM\FieldType\DBForeignKey: | ||
graphql_type: 'ID' |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
<?php | ||
|
||
namespace MyProject; | ||
|
||
use SilverStripe\ORM\DataObject; | ||
|
||
class Comment extends DataObject | ||
{ | ||
private static $db = [ | ||
'Comment' => 'Text', | ||
'Author' => 'Varchar' | ||
]; | ||
|
||
private static $has_one = [ | ||
'Post' => Post::class | ||
]; | ||
|
||
public function canView($member = null, $context = []) { return true; } | ||
public function canEdit($member = null, $context = []) { return true; } | ||
public function canCreate($member = null, $context = []) { return true; } | ||
public function canDelete($member = null, $context = []) { return true; } | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,20 @@ | ||
<?php | ||
|
||
namespace MyProject; | ||
|
||
use SilverStripe\GraphQL\Scaffolding\Interfaces\ResolverInterface; | ||
|
||
class CommentsResolver implements ResolverInterface | ||
{ | ||
public function resolve($object, $args, $context, $info) | ||
{ | ||
$comments = $object->Comments(); | ||
|
||
if(isset($args['Today']) && $args['Today']) { | ||
$comments = $comments->where('DATE(Created) = DATE(NOW())'); | ||
} | ||
|
||
return $comments; | ||
} | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,13 @@ | ||
<?php | ||
|
||
namespace MyProject; | ||
|
||
use SilverStripe\GraphQL\Scaffolding\Interfaces\ResolverInterface; | ||
|
||
class LatestPostResolver implements ResolverInterface | ||
{ | ||
public function resolve($object, $args, $context, $info) | ||
{ | ||
return Post::get()->sort('Date', 'DESC')->first(); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,141 @@ | ||
<?php | ||
|
||
namespace MyProject; | ||
|
||
use SilverStripe\ORM\DataObject; | ||
use SilverStripe\GraphQL\Scaffolding\Interfaces\ScaffoldingProvider; | ||
use SilverStripe\GraphQL\Scaffolding\Scaffolders\SchemaScaffolder; | ||
use SilverStripe\Security\Member; | ||
use SilverStripe\Assets\File; | ||
|
||
class Post extends DataObject implements ScaffoldingProvider | ||
{ | ||
|
||
private static $db = [ | ||
'Title' => 'Varchar', | ||
'Content' => 'HTMLText', | ||
'Date' => 'Datetime' | ||
]; | ||
|
||
private static $has_one = [ | ||
'Author' => Member::class | ||
]; | ||
|
||
private static $many_many = [ | ||
'Files' => File::class | ||
]; | ||
|
||
private static $has_many = [ | ||
'Comments' => Comment::class | ||
]; | ||
|
||
public function provideGraphQLScaffolding(SchemaScaffolder $scaffolder) | ||
{ | ||
$scaffolder | ||
->type(Post::class) | ||
->addFields(['ID', 'Title', 'Content', 'Author', 'Date']) | ||
// basic many_many nested query, no options | ||
->nestedQuery('Files') | ||
->end() | ||
// more complex nested query | ||
->nestedQuery('Comments') | ||
->addArgs([ | ||
'Today' => 'Boolean' | ||
]) | ||
->addSortableFields(['Author']) | ||
->setResolver(function ($obj, $args, $context) { | ||
$comments = $obj->Comments(); | ||
if (isset($args['Today']) && $args['Today']) { | ||
$comments = $comments->where('DATE(Created) = DATE(NOW())'); | ||
} | ||
|
||
return $comments; | ||
}) | ||
->end() | ||
// basic crud operation, no options | ||
->operation(SchemaScaffolder::CREATE) | ||
->end() | ||
// complex crud operation, with custom args | ||
->operation(SchemaScaffolder::READ) | ||
->addArgs([ | ||
'StartingWith' => 'String' | ||
]) | ||
->setResolver(function ($obj, $args) { | ||
$list = Post::get(); | ||
if (isset($args['StartingWith'])) { | ||
$list = $list->filter('Title:StartsWith', $args['StartingWith']); | ||
} | ||
|
||
return $list; | ||
}) | ||
->end() | ||
->end() | ||
// these types were all created implicitly above. Add some fields to them. | ||
->type(Member::class) | ||
->addFields(['Name', 'FirstName', 'Surname', 'Email']) | ||
->end() | ||
->type(File::class) | ||
->addAllFieldsExcept(['Content']) | ||
->addFields(['File']) | ||
->end() | ||
->type(Comment::class) | ||
->addFields(['Comment', 'Author']) | ||
->end() | ||
// Arbitrary mutation | ||
->mutation('updatePostTitle', Post::class) | ||
->addArgs([ | ||
'ID' => 'ID!', | ||
'NewTitle' => 'String!' | ||
]) | ||
->setResolver(function ($obj, $args) { | ||
$post = Post::get()->byID($args['ID']); | ||
if ($post->canEdit()) { | ||
$post->Title = $args['NewTitle']; | ||
$post->write(); | ||
} | ||
|
||
return $post; | ||
}) | ||
->end() | ||
// Arbitrary query | ||
->query('latestPost', Post::class) | ||
->setUsePagination(false) | ||
->setResolver(function ($obj, $args) { | ||
return Post::get()->sort('Date', 'DESC')->first(); | ||
}) | ||
->end() | ||
->type('SilverStripe\CMS\Model\RedirectorPage') | ||
->addFields(['ExternalURL', 'Content']) | ||
->operation(SchemaScaffolder::READ) | ||
->end() | ||
->operation(SchemaScaffolder::CREATE) | ||
->end() | ||
->end() | ||
->type('Page') | ||
->addFields(['BackwardsTitle']) | ||
->end(); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Would be good to have this indented to retain some sanity ;) |
||
|
||
|
||
return $scaffolder; | ||
} | ||
|
||
public function canView($member = null, $context = []) | ||
{ | ||
return true; | ||
} | ||
|
||
public function canEdit($member = null, $context = []) | ||
{ | ||
return true; | ||
} | ||
|
||
public function canCreate($member = null, $context = []) | ||
{ | ||
return true; | ||
} | ||
|
||
public function canDelete($member = null, $context = []) | ||
{ | ||
return true; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,20 @@ | ||
<?php | ||
|
||
namespace MyProject; | ||
|
||
use SilverStripe\GraphQL\Scaffolding\Interfaces\ResolverInterface; | ||
|
||
class ReadResolver implements ResolverInterface | ||
{ | ||
public function resolve($object, $args, $context, $info) | ||
{ | ||
$list = Post::get(); | ||
|
||
if(isset($args['Title'])) { | ||
$list = $list->filter('Title:PartialMatch', $args['Title']); | ||
} | ||
|
||
return $list; | ||
} | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,21 @@ | ||
<?php | ||
|
||
namespace MyProject; | ||
|
||
use SilverStripe\GraphQL\Scaffolding\Interfaces\ResolverInterface; | ||
|
||
class UpdatePostResolver implements ResolverInterface | ||
{ | ||
public function resolve($object, $args, $context, $info) | ||
{ | ||
$post = Post::get()->byID($args['ID']); | ||
|
||
if($post->canEdit()) { | ||
$post->Title = $args['NewTitle']; | ||
$post->write(); | ||
} | ||
|
||
return $post; | ||
} | ||
|
||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Daaaaaamn! That's much easier to digest!