@webresto/graphql 1.3.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (105) hide show
  1. package/.editorconfig +10 -0
  2. package/index.d.ts +3 -0
  3. package/index.js +22 -0
  4. package/index.ts +14 -0
  5. package/lib/afterHook.d.ts +1 -0
  6. package/lib/afterHook.js +24 -0
  7. package/lib/afterHook.ts +26 -0
  8. package/lib/afterHook.ts___graphql-transport-ws +138 -0
  9. package/lib/afterHook.ts___graphql-ws +133 -0
  10. package/lib/defaults.js +12 -0
  11. package/lib/errorWrapper.d.ts +4 -0
  12. package/lib/errorWrapper.js +13 -0
  13. package/lib/errorWrapper.ts +12 -0
  14. package/lib/eventHelper.d.ts +21 -0
  15. package/lib/eventHelper.js +32 -0
  16. package/lib/eventHelper.ts +35 -0
  17. package/lib/graphqlHelper.d.ts +115 -0
  18. package/lib/graphqlHelper.js +596 -0
  19. package/lib/graphqlHelper.ts +692 -0
  20. package/lib/initialize.d.ts +1 -0
  21. package/lib/initialize.js +22 -0
  22. package/lib/initialize.ts +21 -0
  23. package/notes.md +1976 -0
  24. package/package.json +47 -0
  25. package/readme.md +258 -0
  26. package/restApi.http +11 -0
  27. package/src/additionalResolvers.d.ts +19 -0
  28. package/src/additionalResolvers.js +114 -0
  29. package/src/additionalResolvers.ts +111 -0
  30. package/src/graphql.d.ts +7 -0
  31. package/src/graphql.js +144 -0
  32. package/src/graphql.ts +160 -0
  33. package/src/resolvers/cart.d.ts +123 -0
  34. package/src/resolvers/cart.js +176 -0
  35. package/src/resolvers/cart.ts +256 -0
  36. package/src/resolvers/checkout.d.ts +30 -0
  37. package/src/resolvers/checkout.js +226 -0
  38. package/src/resolvers/checkout.ts +242 -0
  39. package/src/resolvers/dishAndModifier.d.ts +2 -0
  40. package/src/resolvers/dishAndModifier.js +35 -0
  41. package/src/resolvers/dishAndModifier.ts +38 -0
  42. package/src/resolvers/maintenance.d.ts +9 -0
  43. package/src/resolvers/maintenance.js +12 -0
  44. package/src/resolvers/maintenance.ts +11 -0
  45. package/src/resolvers/paymentMethod.d.ts +9 -0
  46. package/src/resolvers/paymentMethod.js +22 -0
  47. package/src/resolvers/paymentMethod.ts +20 -0
  48. package/src/resolvers/restrictions.d.ts +9 -0
  49. package/src/resolvers/restrictions.js +24 -0
  50. package/src/resolvers/restrictions.ts +22 -0
  51. package/src/resolvers/streets.d.ts +9 -0
  52. package/src/resolvers/streets.js +16 -0
  53. package/src/resolvers/streets.ts +13 -0
  54. package/src/resolvers/subscriptions.d.ts +33 -0
  55. package/src/resolvers/subscriptions.js +52 -0
  56. package/src/resolvers/subscriptions.ts +63 -0
  57. package/test/.eslintrc +8 -0
  58. package/test/_bootstrap.js +29 -0
  59. package/test/fixtures/v0.12-app/.gitignore +11 -0
  60. package/test/fixtures/v0.12-app/.sailsrc +11 -0
  61. package/test/fixtures/v0.12-app/api/controllers/.gitkeep +0 -0
  62. package/test/fixtures/v0.12-app/api/models/.gitkeep +0 -0
  63. package/test/fixtures/v0.12-app/api/models/TestModel.js +22 -0
  64. package/test/fixtures/v0.12-app/api/responses/badRequest.js +76 -0
  65. package/test/fixtures/v0.12-app/api/responses/created.js +60 -0
  66. package/test/fixtures/v0.12-app/api/responses/forbidden.js +89 -0
  67. package/test/fixtures/v0.12-app/api/responses/notFound.js +94 -0
  68. package/test/fixtures/v0.12-app/api/responses/ok.js +60 -0
  69. package/test/fixtures/v0.12-app/api/responses/serverError.js +89 -0
  70. package/test/fixtures/v0.12-app/api/services/.gitkeep +0 -0
  71. package/test/fixtures/v0.12-app/app.js +73 -0
  72. package/test/fixtures/v0.12-app/config/bootstrap.js +6 -0
  73. package/test/fixtures/v0.12-app/config/connections.js +5 -0
  74. package/test/fixtures/v0.12-app/config/cors.js +78 -0
  75. package/test/fixtures/v0.12-app/config/csrf.js +64 -0
  76. package/test/fixtures/v0.12-app/config/env/development.js +10 -0
  77. package/test/fixtures/v0.12-app/config/env/production.js +16 -0
  78. package/test/fixtures/v0.12-app/config/globals.js +63 -0
  79. package/test/fixtures/v0.12-app/config/hookTimeout.js +8 -0
  80. package/test/fixtures/v0.12-app/config/http.js +93 -0
  81. package/test/fixtures/v0.12-app/config/i18n.js +57 -0
  82. package/test/fixtures/v0.12-app/config/log.js +29 -0
  83. package/test/fixtures/v0.12-app/config/models.js +3 -0
  84. package/test/fixtures/v0.12-app/config/policies.js +51 -0
  85. package/test/fixtures/v0.12-app/config/restoapi.js +3 -0
  86. package/test/fixtures/v0.12-app/config/restocore.js +39 -0
  87. package/test/fixtures/v0.12-app/config/routes.js +49 -0
  88. package/test/fixtures/v0.12-app/config/session.js +100 -0
  89. package/test/fixtures/v0.12-app/config/sockets.js +141 -0
  90. package/test/fixtures/v0.12-app/config/stateflow.js +4 -0
  91. package/test/fixtures/v0.12-app/config/views.js +95 -0
  92. package/test/fixtures/v0.12-app/package.json +34 -0
  93. package/test/fixtures/v0.12-app/views/403.ejs +68 -0
  94. package/test/fixtures/v0.12-app/views/404.ejs +68 -0
  95. package/test/fixtures/v0.12-app/views/500.ejs +73 -0
  96. package/test/fixtures/v0.12-app/views/homepage.ejs +74 -0
  97. package/test/fixtures/v0.12-app/views/layout.ejs +91 -0
  98. package/test/mocha.opts +2 -0
  99. package/test/readme.md +0 -0
  100. package/test/todo +0 -0
  101. package/test/tslint.json +18 -0
  102. package/test/unit/first.test.js +11 -0
  103. package/test/unit/sails_not_crash.test.js +3 -0
  104. package/todo.md +1 -0
  105. package/tsconfig.json +10 -0
@@ -0,0 +1,256 @@
1
+ import * as eventHelper from "@webresto/graphql";
2
+ import checkExpression from "@webresto/core/libs/checkExpression";
3
+ import getEmitter from "@webresto/core/libs/getEmitter";
4
+
5
+ import { Error } from "../../lib/errorWrapper";
6
+
7
+ export default {
8
+ Query: {
9
+ order: {
10
+ def: '""" если orderId не задан, вернется новая корзина """ order(orderId: String, shortId: String, orderNumber: String): Order',
11
+ fn: async function (parent, args, context) {
12
+ let order;
13
+
14
+ let criteria = {};
15
+ if (args.orderNumber) {
16
+ criteria["rmsOrderNumber"] = args.orderNumber;
17
+ criteria["sort"] = "createdAt DESC";
18
+ } else if (args.orderId) {
19
+ criteria["id"] = args.orderId;
20
+ } else if (args.shortId) {
21
+ criteria["shortId"] = args.shortId;
22
+ }
23
+
24
+ if (Object.keys(criteria).length !== 0) {
25
+ order = (await Order.find(criteria))[0];
26
+ }
27
+
28
+ if (!order) {
29
+ sails.log.error(
30
+ "GQL > order resolver error: ",
31
+ `order with id ${args.orderId} . Trying make new cart.`
32
+ );
33
+ order = await getNewCart(args.orderId);
34
+ }
35
+ return await Order.populate(order.id);
36
+ },
37
+ },
38
+ },
39
+ Mutation: {
40
+ orderAddDish: {
41
+ def: "orderAddDish(orderId: String, dishId: String, amount: Int, modifiers: Json, comment: String, from: String, replace: Boolean, orderDishId: Int): Order",
42
+ fn: async function (parent, args, context) {
43
+ let order;
44
+
45
+ if (args.modifiers) {
46
+ args.modifiers.forEach((modifier) => {
47
+ if (modifier.amount === undefined || modifier.id === undefined)
48
+ throw new Error(
49
+ 0,
50
+ "ERROR",
51
+ `modifier required (amount, id) for dish: ${args.dishId} current values: id: ${modifier.id}, amount: ${modifier.amount}`
52
+ );
53
+ });
54
+ }
55
+
56
+ if (args.orderId) order = await Order.findOne({ id: args.orderId });
57
+
58
+ if (!order) {
59
+ sails.log.error(
60
+ "GQL > orderAddDish resolver error: ",
61
+ `order with id ${args.orderId} has problem. Trying make new cart.`
62
+ );
63
+ order = await getNewCart(args.orderId);
64
+ }
65
+
66
+ const dish = await Dish.findOne({ id: args.dishId });
67
+
68
+ if (!dish && !args.replace)
69
+ throw new Error(0, "ERROR", `dish with id ${args.dishId} not found`);
70
+
71
+ if (dish && checkExpression(dish) === "promo") {
72
+ let additionalInfo;
73
+ try {
74
+ additionalInfo = JSON.parse(dish.additionalInfo);
75
+ } catch (e) {}
76
+
77
+ if (additionalInfo && additionalInfo.defaultOrderDish) {
78
+ // Исключение на товар в каждую корзину
79
+ } else {
80
+ throw new Error(
81
+ 0,
82
+ "ERROR",
83
+ `"${dish.name}" является акционным и не может быть добавлено пользователем`
84
+ );
85
+ }
86
+ }
87
+
88
+ await Order.addDish(
89
+ order.id,
90
+ args.dishId,
91
+ args.amount,
92
+ args.modifiers || [],
93
+ args.comment,
94
+ args.from,
95
+ args.replace,
96
+ args.orderDishId
97
+ );
98
+ return await Order.countCart(order);
99
+ },
100
+ },
101
+ orderReplaceDish: {
102
+ def: "orderReplaceDish(orderId: String!, orderDishId: Int!, amount: Int, modifiers: Json, comment: String, from: String): Order",
103
+ fn: async (parent, args, context) => {
104
+ let order;
105
+ if (args.orderId) order = await Order.findOne({ id: args.orderId });
106
+
107
+ if (!order) {
108
+ sails.log.error(
109
+ "GQL > orderReplaceDish resolver error: ",
110
+ `order with id ${args.orderId} has problem. Trying make new cart.`
111
+ );
112
+ order = await getNewCart(args.orderId);
113
+ }
114
+
115
+ if (order.paid || order.state === "ORDER") {
116
+ order = await getNewCart();
117
+ }
118
+
119
+ await Order.addDish(
120
+ order.id,
121
+ args.dishId,
122
+ args.amount,
123
+ args.modifiers || [],
124
+ args.comment,
125
+ args.from,
126
+ args.replace,
127
+ args.orderDishId
128
+ );
129
+ return await Order.countCart(order);
130
+ },
131
+ },
132
+ orderRemoveDish: {
133
+ def: "orderRemoveDish(id: String!, orderDishId: Int!, amount: Int): Order",
134
+ fn: async function (parent, args, context) {
135
+ let order;
136
+ order = await Order.findOne({ id: args.id });
137
+
138
+ if (!order) {
139
+ sails.log.error(
140
+ "GQL > orderRemoveDish resolver error: ",
141
+ `order with id ${args.orderId} has problem. Trying make new cart.`
142
+ );
143
+ order = await getNewCart(args.orderId);
144
+ }
145
+
146
+ if (order.paid || order.state === "ORDER") {
147
+ order = await getNewCart();
148
+ }
149
+
150
+ const orderDish = await OrderDish.findOne({ id: args.orderDishId });
151
+
152
+ await Order.removeDish(order.id, orderDish, args.amount, false);
153
+ return await Order.countCart(order);
154
+ },
155
+ },
156
+ orderSetDishAmount: {
157
+ def: "orderSetDishAmount(id: String, orderDishId: Int, amount: Int): Order",
158
+ fn: async function (parent, args, context) {
159
+ let order;
160
+
161
+ order = await Order.findOne(args.id);
162
+
163
+ if (!order) {
164
+ sails.log.error(
165
+ "GQL > orderSetDishAmount resolver error: ",
166
+ `order with id ${args.orderId} has problem. Trying make new cart.`
167
+ );
168
+ order = await getNewCart(args.orderId);
169
+ }
170
+
171
+ if (order.paid || order.state === "ORDER") {
172
+ order = await getNewCart();
173
+ }
174
+
175
+ let dish = await OrderDish.findOne(args.orderDishId).populate("dish");
176
+ if (!dish)
177
+ throw new Error(
178
+ 0,
179
+ "ERROR",
180
+ `OrderDish with id ${args.orderDishId} not found`
181
+ );
182
+ if (!dish.dish)
183
+ throw new Error(
184
+ 0,
185
+ "ERROR",
186
+ `Dish in OrderDish with id ${args.orderDishId} not found`
187
+ );
188
+
189
+ await Order.setCount(order.id, dish, args.amount);
190
+ return await Order.countCart(order);
191
+ },
192
+ },
193
+ orderSetDishComment: {
194
+ def: "orderSetDishComment(id: String, orderDishId: Int, comment: String): Order",
195
+ fn: async function (parent, args, context) {
196
+ let order;
197
+
198
+ const data = args;
199
+ const orderId = data.orderId;
200
+ const comment = data.comment || "";
201
+ const dishId = data.dishId;
202
+ if (!dishId) {
203
+ throw new Error(0, "ERROR", "dishId is required");
204
+ }
205
+
206
+ order = await Order.findOne(orderId);
207
+
208
+ if (!order) {
209
+ sails.log.error(
210
+ "GQL > orderSetDishComment resolver error: ",
211
+ `order with id ${args.orderId} has problem. Trying make new cart.`
212
+ );
213
+ order = await getNewCart(args.orderId);
214
+ }
215
+
216
+ if (order.paid || order.state === "ORDER") {
217
+ order = await getNewCart();
218
+ }
219
+
220
+ const dish = await OrderDish.findOne({ id: dishId }).populate("dish");
221
+ if (!dish) {
222
+ throw new Error(0, "ERROR", `Dish with id ${dishId} not found`);
223
+ }
224
+
225
+ await order.setComment(dish, comment);
226
+ return await Order.countCart(order);
227
+ },
228
+ },
229
+
230
+ orderUpdate: {
231
+ def: '"""Experimental! allowed only for trifleFrom """ orderUpdate(order: Json): Order',
232
+ fn: async function (parent, args, context) {
233
+
234
+ let order = args.order;
235
+ if (!order.id) throw "order.id field is required"
236
+ await Order.update({id: order.id}, {trifleFrom: order.trifleFrom})
237
+ return await Order.populate(order.id);
238
+ },
239
+ },
240
+ },
241
+ };
242
+
243
+ // Generate new cart
244
+ async function getNewCart(orderId?: string) {
245
+ let order: any;
246
+ let initOrder = {};
247
+
248
+ // Pass oredrId from frontend
249
+ if (orderId) initOrder["id"] = orderId;
250
+
251
+ getEmitter().emit("http-api:init-newcart", initOrder);
252
+ order = await Order.create(initOrder).fetch();
253
+ await getEmitter().emit("http-api:create-newcart", order);
254
+
255
+ return order;
256
+ }
@@ -0,0 +1,30 @@
1
+ declare const _default: {
2
+ Mutation: {
3
+ checkOrder: {
4
+ def: string;
5
+ fn: (parent: any, args: any, context: any) => Promise<void | {
6
+ order: import("@webresto/core/models/Order").default;
7
+ message?: undefined;
8
+ } | {
9
+ message: {
10
+ type: string;
11
+ title: string;
12
+ message: string;
13
+ };
14
+ order?: undefined;
15
+ }>;
16
+ };
17
+ sendOrder: {
18
+ def: string;
19
+ fn: (parent: any, args: any, context: any) => Promise<{
20
+ order: import("@webresto/core/models/Order").default;
21
+ message: {
22
+ type: string;
23
+ title: string;
24
+ message: string;
25
+ };
26
+ }>;
27
+ };
28
+ };
29
+ };
30
+ export default _default;
@@ -0,0 +1,226 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const eventHelper = require("../../lib/eventHelper");
4
+ const errorWrapper_1 = require("../../lib/errorWrapper");
5
+ exports.default = {
6
+ Mutation: {
7
+ checkOrder: {
8
+ def: "checkOrder(orderId: String!, paymentMethodId: String!, selfService: Boolean, address: Address, customer: Customer!, date: String, comment: String, customData: Json): CheckResponse",
9
+ fn: async function (parent, args, context) {
10
+ let data = args;
11
+ // if (data.date) {
12
+ // let date = moment(data.date)
13
+ // if(!date.isValid()){
14
+ // return eventHelper.sendMessage(args.orderId, "Please order.date format is ISO (YYYY-MM-DD HH:mm:ss)");
15
+ // } else {
16
+ // data.date = date.format('YYYY-MM-DD HH:mm:ss');
17
+ // }
18
+ // }
19
+ let isSelfService;
20
+ //@ts-ignore
21
+ if (data.selfService || data.selfDelivery) {
22
+ isSelfService = true;
23
+ }
24
+ try {
25
+ var order = await Order.findOne(data.orderId);
26
+ if (!order) {
27
+ return eventHelper.sendMessage(args.orderId, {
28
+ type: "error",
29
+ title: "Order not found",
30
+ message: `Order with id ${data.orderId} not found`,
31
+ });
32
+ }
33
+ if (order.state === "ORDER") {
34
+ return eventHelper.sendMessage(args.orderId, {
35
+ type: "error",
36
+ title: "Ошибка",
37
+ message: "Корзина уже заказана",
38
+ });
39
+ }
40
+ if (data.paymentMethodId) {
41
+ if (!PaymentMethod.checkAvailable(data.paymentMethodId)) {
42
+ return eventHelper.sendMessage(args.orderId, {
43
+ type: "error",
44
+ title: "Ошибка",
45
+ message: "Проверка платежной системы завершилась неудачей",
46
+ });
47
+ }
48
+ }
49
+ if (data.address) {
50
+ data.address.city =
51
+ data.address.city || (await Settings.use("city"));
52
+ }
53
+ order.personsCount = data.personsCount ? data.personsCount : "";
54
+ if (data.comment)
55
+ order.comment = data.comment;
56
+ if (data.date)
57
+ order.date = data.date;
58
+ // callback: boolean - перезвонить для уточнения деталей
59
+ if (data.customData && data.customData.callback) {
60
+ if (!order.customData)
61
+ order.customData = {};
62
+ order.customData.callback = data.customData.callback;
63
+ }
64
+ await Order.update({ id: order.id }, order).fetch();
65
+ let success;
66
+ success = await Order.check(order.id, data.customer, isSelfService, data.address, data.paymentMethodId);
67
+ order = await Order.findOne(data.orderId).populateAll();
68
+ let message;
69
+ if (success && order.state === "CHECKOUT") {
70
+ message = {
71
+ type: "info",
72
+ title: "Внимание",
73
+ message: order.message
74
+ ? order.message
75
+ : "Заказ готов к оформлению",
76
+ };
77
+ }
78
+ else {
79
+ if (order.message) {
80
+ return eventHelper.sendMessage(args.orderId, {
81
+ type: "error",
82
+ title: "Внимание",
83
+ message: order.message
84
+ ? order.message
85
+ : "Не удалось проверить заказ.",
86
+ });
87
+ }
88
+ }
89
+ return { order: order };
90
+ }
91
+ catch (e) {
92
+ let message = {
93
+ type: "error",
94
+ title: "Ошибка",
95
+ message: "",
96
+ };
97
+ if (e.code === 1) {
98
+ message.message = "Введите имя заказчика";
99
+ }
100
+ else if (e.code === 2) {
101
+ message.message = "Введите телефон заказчика";
102
+ }
103
+ else if (e.code === 3) {
104
+ message.message = "Неверный формат имени заказчика";
105
+ }
106
+ else if (e.code === 4) {
107
+ message.message = "Неверный формат номера заказчика";
108
+ }
109
+ else if (e.code === 5) {
110
+ message.message = "Не указана улица";
111
+ }
112
+ else if (e.code === 6) {
113
+ message.message = "Не указан номер дома";
114
+ }
115
+ else if (e.code === 7) {
116
+ message.message = "Не указан город";
117
+ }
118
+ else if (e.code === 8) {
119
+ message.message = "Платежная система недоступна";
120
+ }
121
+ else if (e.code === 10) {
122
+ message.message = "Дата выполнения заказа не верная";
123
+ }
124
+ else {
125
+ message.message = e.error
126
+ ? e.error
127
+ : `Проблема при проверки заказа: ${e}`;
128
+ }
129
+ eventHelper.sendMessage(args.orderId, message);
130
+ sails.log.error(e);
131
+ return { message: message };
132
+ }
133
+ },
134
+ },
135
+ sendOrder: {
136
+ def: "sendOrder(orderId: String!): CheckResponse",
137
+ fn: async function (parent, args, context) {
138
+ let data = args;
139
+ // if (data.date) {
140
+ // let date = moment(data.date)
141
+ // if(!date.isValid()){
142
+ // return eventHelper.sendMessage(args.orderId,"Please order.date format is ISO (YYYY-MM-DD HH:mm:ss)");
143
+ // } else {
144
+ // data.date = date.format('YYYY-MM-DD HH:mm:ss');
145
+ // }
146
+ // }
147
+ try {
148
+ var order = await Order.findOne({ id: data.orderId });
149
+ if (!order) {
150
+ const errorMessage = `Order with id ${data.orderId} not found`;
151
+ eventHelper.sendMessage(args.orderId, {
152
+ type: "error",
153
+ title: "Order not found",
154
+ message: errorMessage,
155
+ });
156
+ sails.log.error(`${errorMessage}`);
157
+ throw new errorWrapper_1.Error(0, errorMessage);
158
+ }
159
+ // if (data.comment) order.comment = data.comment;
160
+ // if (data.paymentMethodId) {
161
+ // if (order.paymentMethod !== data.paymentMethodId) {
162
+ // await Order.check(
163
+ // order.id,
164
+ // null,
165
+ // null,
166
+ // null,
167
+ // data.paymentMethodId
168
+ // );
169
+ // order = await Order.findOne({ id: data.orderId });
170
+ // }
171
+ // }
172
+ // if (order.paymentMethod) {
173
+ // if (!(await PaymentMethod.checkAvailable(order.paymentMethod))) {
174
+ // let errorMessage = `Проверка платежной системы завершилась неудачно`;
175
+ // eventHelper.sendMessage(args.orderId, {
176
+ // type: "error",
177
+ // title: "Ошибка",
178
+ // message: errorMessage,
179
+ // });
180
+ // sails.log.error(`${errorMessage}`)
181
+ // throw new Error(0,errorMessage);
182
+ // }
183
+ // if (!(await PaymentMethod.isPaymentPromise(data.paymentMethodId))) {
184
+ // try {
185
+ // let paymentResponse = await order.payment();
186
+ // const action = {
187
+ // type: "PaymentRedirect",
188
+ // data: {
189
+ // redirectLink: paymentResponse.redirectLink,
190
+ // },
191
+ // };
192
+ // eventHelper.sendAction(args.orderId, action);
193
+ // return { order: order, action: action };
194
+ // } catch (e) {
195
+ // eventHelper.sendMessage(args.orderId, {
196
+ // type: "error",
197
+ // title: "Ошибка",
198
+ // message: "Попытка регистрации платежа завершилась неудачно",
199
+ // });
200
+ // sails.log.error(e);
201
+ // throw new Error(0, JSON.stringify(e));
202
+ // }
203
+ // }
204
+ // }
205
+ await Order.order(order.id);
206
+ const message = {
207
+ type: "info",
208
+ title: "Успешно",
209
+ message: "Ваш заказ принят в обработку",
210
+ };
211
+ eventHelper.sendMessage(args.orderId, message);
212
+ return { order: order, message: message };
213
+ }
214
+ catch (e) {
215
+ eventHelper.sendMessage(args.orderId, {
216
+ type: "error",
217
+ title: "Ошибка",
218
+ message: e,
219
+ });
220
+ sails.log.error("sendOrder error :", e);
221
+ throw new errorWrapper_1.Error(0, `${e}`);
222
+ }
223
+ },
224
+ },
225
+ },
226
+ };