• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

wp-graphql / wp-graphql-woocommerce / 5944127059

22 Aug 2023 09:14PM UTC coverage: 82.865% (-0.03%) from 82.898%
5944127059

push

github

web-flow
fix: ProductVariation type made to inherit the Product interface. (#788)

* devops: WP theme during e2e locked to TwentyTwentyOne

* fix: "Product Connection Resolver" restored

* chore: Linter/PHPStan compliance met

* devops: CustomerProceedsToCheckoutCept updated.

* chore: Linter compliance met

216 of 216 new or added lines in 9 files covered. (100.0%)

10296 of 12425 relevant lines covered (82.87%)

54.38 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

66.67
/includes/data/loader/class-wc-cpt-loader.php
1
<?php
2
/**
3
 * DataLoader - WC_CPT_Loader
4
 *
5
 * Loads Models for WooCommerce CPTs
6
 *
7
 * @package WPGraphQL\WooCommerce\Data\Loader
8
 * @since 0.0.1
9
 */
10

11
namespace WPGraphQL\WooCommerce\Data\Loader;
12

13
use Automattic\WooCommerce\Utilities\OrderUtil;
14
use GraphQL\Error\UserError;
15
use WPGraphQL\Data\Loader\AbstractDataLoader;
16
use WPGraphQL\WooCommerce\Model\Coupon;
17
use WPGraphQL\WooCommerce\Model\Order;
18
use WPGraphQL\WooCommerce\Model\Product;
19
use WPGraphQL\WooCommerce\Model\Product_Variation;
20
use WPGraphQL\WooCommerce\WP_GraphQL_WooCommerce;
21

22
/**
23
 * Class WC_CPT_Loader
24
 */
25
class WC_CPT_Loader extends AbstractDataLoader {
26
        /**
27
         * Returns the Model for a given post-type and ID.
28
         *
29
         * @param string  $post_type  WordPress post-type.
30
         * @param int     $id         Post ID.
31
         * @param boolean $fatal      Throw if no model found.
32
         *
33
         * @throws \GraphQL\Error\UserError - throws if no corresponding Model is registered to the post-type.
34
         * 
35
         * @return \WPGraphQL\Model\Model|null
36
         */
37
        public static function resolve_model( $post_type, $id, $fatal = true ) {
38
                switch ( $post_type ) {
39
                        case 'product':
81✔
40
                                return new Product( $id );
53✔
41
                        case 'product_variation':
50✔
42
                                return new Product_Variation( $id );
19✔
43
                        case 'shop_coupon':
36✔
44
                                return new Coupon( $id );
10✔
45
                        case 'shop_order':
27✔
46
                        case 'shop_order_refund':
27✔
47
                        case 'shop_order_placehold':
27✔
48
                                return new Order( $id );
22✔
49
                        default:
50
                                $model = apply_filters( 'graphql_woocommerce_cpt_loader_model', null, $post_type );
5✔
51
                                if ( ! empty( $model ) ) {
5✔
52
                                        /**
53
                                         * If a model is registered to the post-type, we can return an instance of that model
54
                                         * with the post ID passed in.
55
                                         * 
56
                                         * @var \WPGraphQL\Model\Model
57
                                         */
58
                                        return new $model( $id );
×
59
                                }
60

61
                                // Bail if not fatal.
62
                                if ( ! $fatal ) {
5✔
63
                                        return null;
5✔
64
                                }
65

66
                                /* translators: no model assigned error message */
67
                                throw new UserError( sprintf( __( 'No Model is register to the custom post-type "%s"', 'wp-graphql-woocommerce' ), $post_type ) );
×
68
                }//end switch
69
        }
70

71
        /**
72
         * {@inheritDoc}
73
         *
74
         * @throws \GraphQL\Error\UserError - throws if the post-type is not a valid WooCommerce post-type.
75
         */
76
        public function loadKeys( array $keys ) {
77
                if ( empty( $keys ) ) {
66✔
78
                        return $keys;
×
79
                }
80

81
                $wc_post_types = WP_GraphQL_WooCommerce::get_post_types();
66✔
82
                /**
83
                 * Prepare the args for the query. We're provided a specific
84
                 * set of IDs, so we want to query as efficiently as possible with
85
                 * as little overhead as possible. We don't want to return post counts,
86
                 * we don't want to include sticky posts, and we want to limit the query
87
                 * to the count of the keys provided. The query must also return results
88
                 * in the same order the keys were provided in.
89
                 */
90
                $args = [
66✔
91
                        'post_type'           => $wc_post_types,
66✔
92
                        'post_status'         => 'any',
66✔
93
                        //phpcs:ignore WordPress.WP.PostsPerPage.posts_per_page_posts_per_page
94
                        'posts_per_page'      => count( $keys ),
66✔
95
                        'post__in'            => $keys,
66✔
96
                        'orderby'             => 'post__in',
66✔
97
                        'no_found_rows'       => true,
66✔
98
                        'split_the_query'     => false,
66✔
99
                        'ignore_sticky_posts' => true,
66✔
100
                ];
66✔
101

102
                /**
103
                 * Ensure that WP_Query doesn't first ask for IDs since we already have them.
104
                 */
105
                add_filter(
66✔
106
                        'split_the_query',
66✔
107
                        static function ( $split, \WP_Query $query ) {
66✔
108
                                if ( false === $query->get( 'split_the_query' ) ) {
66✔
109
                                        return false;
66✔
110
                                }
111
                                return $split;
×
112
                        },
66✔
113
                        10,
66✔
114
                        2
66✔
115
                );
66✔
116
                new \WP_Query( $args );
66✔
117

118
                $loaded_posts = [];
66✔
119

120
                /**
121
                 * Loop over the posts and return an array of all_posts,
122
                 * where the key is the ID and the value is the Post passed through
123
                 * the model layer.
124
                 */
125
                foreach ( $keys as $key ) {
66✔
126
                        /**
127
                         * The query above has added our objects to the cache
128
                         * so now we can pluck them from the cache to return here
129
                         * and if they don't exist or aren't a valid post-type we can throw an error, otherwise
130
                         * we can proceed to resolve the object via the Model layer.
131
                         */
132
                        $post_type = get_post_type( $key );
66✔
133
                        if ( ! $post_type ) {
66✔
134
                                $loaded_posts[ $key ] = null;
×
135
                                continue;
×
136
                        }
137

138
                        if ( ! in_array( $post_type, $wc_post_types, true ) && ! OrderUtil::is_order( $key, wc_get_order_types() ) ) {
66✔
139
                                /* translators: invalid post-type error message */
140
                                throw new UserError( sprintf( __( '%s is not a valid WooCommerce post-type', 'wp-graphql-woocommerce' ), $post_type ) );
×
141
                        }
142

143
                        $post_object = get_post( (int) $key );
66✔
144
                        if ( ! $post_object instanceof \WP_Post ) {
66✔
145
                                $loaded_posts[ $key ] = null;
×
146
                        } else {
147
                                $loaded_posts[ $key ] = $post_object;
66✔
148
                        }
149
                }//end foreach
150

151
                return $loaded_posts;
66✔
152
        }
153

154
        /**
155
         * {@inheritDoc}
156
         * 
157
         * @return \WPGraphQL\Model\Model|null
158
         */
159
        protected function get_model( $entry, $key ) {
160
                if ( ! $entry ) {
×
161
                        return null;
×
162
                }
163

164
                /**
165
                 * If there's a customer connected to the order, we need to resolve the
166
                 * customer
167
                 */
168
                $context = $this->context;
×
169

170
                // Resolve post author for future capability checks.
171
                switch ( $entry->post_type ) {
×
172
                        case 'shop_order':
×
173
                                $customer_id = get_post_meta( $key, '_customer_user', true );
×
174
                                if ( ! empty( $customer_id ) ) {
×
175
                                        $context->get_loader( 'wc_customer' )->load_deferred( $customer_id );
×
176
                                }
177
                                break;
×
178
                        case 'product_variation':
×
179
                        case 'shop_refund':
×
180
                                $parent_id = $entry->post_parent;
×
181
                                if ( ! empty( $entry->post_parent ) ) {
×
182
                                        $context->get_loader( 'wc_post' )->load_deferred( $entry->post_parent );
×
183
                                }
184
                                break;
×
185
                }
186

187
                return self::resolve_model( $entry->post_type, $key, false );
×
188
        }
189

190
        /**
191
         * Callback for inject the PostObject dataloader with WC_Post models.
192
         *
193
         * @param null  $model  Possible model instance to be loader.
194
         * @param mixed $entry  Data source.
195
         * @param mixed $key    Data key/ID.
196
         * @return \WPGraphQL\Model\Model|null
197
         */
198
        public static function inject_post_loader_models( $model, $entry, $key ) {
199
                if ( is_a( $entry, \WP_Post::class ) ) {
87✔
200
                        $model = self::resolve_model( $entry->post_type, $key, false );
75✔
201
                }
202

203
                return $model;
87✔
204
        }
205
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc