decidim-api 0.31.4 → 0.32.0.rc1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (52) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +3 -13
  3. data/app/controllers/decidim/api/sessions_controller.rb +1 -1
  4. data/app/models/decidim/api/api_user.rb +5 -1
  5. data/config/locales/ca-IT.yml +7 -0
  6. data/config/locales/ca.yml +7 -0
  7. data/config/locales/cs.yml +7 -0
  8. data/config/locales/el.yml +11 -0
  9. data/config/locales/en.yml +7 -0
  10. data/config/locales/es-MX.yml +7 -0
  11. data/config/locales/es-PY.yml +7 -0
  12. data/config/locales/es.yml +7 -0
  13. data/config/locales/eu.yml +7 -0
  14. data/config/locales/fi-plain.yml +7 -0
  15. data/config/locales/fi.yml +7 -0
  16. data/config/locales/fr-CA.yml +4 -0
  17. data/config/locales/fr.yml +4 -0
  18. data/config/locales/ja.yml +7 -0
  19. data/config/locales/no.yml +1 -0
  20. data/config/locales/pt-BR.yml +7 -0
  21. data/config/locales/ro-RO.yml +7 -0
  22. data/config/locales/sv.yml +7 -0
  23. data/decidim-api.gemspec +12 -15
  24. data/docs/usage.md +3 -634
  25. data/lib/decidim/api/component_mutation_type.rb +1 -2
  26. data/lib/decidim/api/errors/attribute_validation_error.rb +73 -0
  27. data/lib/decidim/api/errors/invalid_locale_error.rb +14 -0
  28. data/lib/decidim/api/errors/locale_error.rb +14 -0
  29. data/lib/decidim/api/errors/mutation_not_authorized_error.rb +14 -0
  30. data/lib/decidim/api/errors/not_found_error.rb +14 -0
  31. data/lib/decidim/api/errors/permission_not_set_error.rb +14 -0
  32. data/lib/decidim/api/errors/unauthorized_field_error.rb +14 -0
  33. data/lib/decidim/api/errors/unauthorized_object_error.rb +14 -0
  34. data/lib/decidim/api/errors/validation_error.rb +13 -0
  35. data/lib/decidim/api/graphiql/config.rb +1 -1
  36. data/lib/decidim/api/graphql_permissions.rb +17 -12
  37. data/lib/decidim/api/query_type.rb +91 -0
  38. data/lib/decidim/api/schema.rb +27 -1
  39. data/lib/decidim/api/test/component_context.rb +59 -51
  40. data/lib/decidim/api/test/shared_examples/commentable_interface_examples.rb +46 -0
  41. data/lib/decidim/api/test/shared_examples/followable_interface_examples.rb +12 -1
  42. data/lib/decidim/api/test/shared_examples/statistics_examples.rb +0 -2
  43. data/lib/decidim/api/test/type_context.rb +10 -2
  44. data/lib/decidim/api/test.rb +1 -0
  45. data/lib/decidim/api/types/access_mode_enum.rb +15 -0
  46. data/lib/decidim/api/types/base_mutation.rb +28 -0
  47. data/lib/decidim/api/types/base_object.rb +12 -0
  48. data/lib/decidim/api/types.rb +12 -1
  49. data/lib/decidim/api/version.rb +1 -1
  50. data/lib/decidim/api.rb +22 -32
  51. metadata +59 -34
  52. /data/lib/decidim/api/test/{mutation_context.rb → shared_examples/mutation_context.rb} +0 -0
@@ -43,25 +43,33 @@ shared_context "with a graphql decidim component" do
43
43
  end
44
44
  end
45
45
 
46
- shared_examples "with resource visibility" do
47
- let(:process_space_factory) { :participatory_process }
46
+ shared_examples "graphQL not found space" do
48
47
  let(:space_type) { "participatoryProcess" }
49
48
 
50
- shared_examples "graphQL visible resource" do
51
- it "is visible" do
52
- expect(response[space_type]["components"].first[lookout_key]).to eq(query_result)
53
- end
49
+ it "should not be visible" do
50
+ expect { response }.to raise_error(Decidim::Api::Errors::NotFoundError, "#{space_type.classify} not found")
54
51
  end
52
+ end
55
53
 
56
- shared_examples "graphQL hidden space" do
57
- it "should not be visible" do
58
- expect(response[space_type]).to be_nil
54
+ shared_examples "with resource visibility" do
55
+ let(:process_space_factory) { :participatory_process }
56
+ let(:space_type) { "participatoryProcess" }
57
+
58
+ shared_examples "graphQL visible resource" do |visible: true|
59
+ if visible
60
+ it "should be visible" do
61
+ expect(response[space_type]["components"].first[lookout_key]).to eq(query_result)
62
+ end
63
+ else
64
+ it "should not be visible" do
65
+ expect(response[space_type]["components"]).to be_empty
66
+ end
59
67
  end
60
68
  end
61
69
 
62
70
  shared_examples "graphQL hidden component" do
63
71
  it "should not be visible" do
64
- expect(response[space_type]["components"].first).to be_nil
72
+ expect(response[space_type]["components"]).to be_empty
65
73
  end
66
74
  end
67
75
 
@@ -76,7 +84,7 @@ shared_examples "with resource visibility" do
76
84
  shared_examples "graphQL space hidden to visitor" do
77
85
  context "when user is visitor" do
78
86
  let!(:current_user) { nil }
79
- it_behaves_like "graphQL hidden space"
87
+ it_behaves_like "graphQL not found space"
80
88
  end
81
89
  end
82
90
 
@@ -119,13 +127,13 @@ shared_examples "with resource visibility" do
119
127
 
120
128
  context "when user is member" do
121
129
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
122
- let!(:participatory_space_private_user) { create(:participatory_space_private_user, user: current_user, privatable_to: participatory_process) }
130
+ let!(:member) { create(:member, user: current_user, participatory_space: participatory_process) }
123
131
  it_behaves_like "graphQL visible resource"
124
132
  end
125
133
 
126
134
  context "when user is member" do
127
135
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
128
- let!(:participatory_space_private_user) { create(:participatory_space_private_user, user: current_user, privatable_to: participatory_process) }
136
+ let!(:member) { create(:member, user: current_user, participatory_space: participatory_process) }
129
137
  it_behaves_like "graphQL visible resource"
130
138
  end
131
139
 
@@ -143,7 +151,7 @@ shared_examples "with resource visibility" do
143
151
  context "when the user is space admin" do
144
152
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
145
153
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "admin") }
146
- it_behaves_like "graphQL visible resource"
154
+ it_behaves_like "graphQL visible resource", visible: false
147
155
  end
148
156
 
149
157
  context "when the user is space collaborator" do
@@ -161,7 +169,7 @@ shared_examples "with resource visibility" do
161
169
  context "when the user is space evaluator" do
162
170
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
163
171
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "evaluator") }
164
- it_behaves_like "graphQL visible resource"
172
+ it_behaves_like "graphQL visible resource", visible: false
165
173
  end
166
174
 
167
175
  context "when user is visitor" do
@@ -177,13 +185,13 @@ shared_examples "with resource visibility" do
177
185
 
178
186
  context "when user is member" do
179
187
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
180
- let!(:participatory_space_private_user) { create(:participatory_space_private_user, user: current_user, privatable_to: participatory_process) }
188
+ let!(:member) { create(:member, user: current_user, participatory_space: participatory_process) }
181
189
  it_behaves_like "graphQL hidden component"
182
190
  end
183
191
  end
184
192
  end
185
193
 
186
- context "when space is published, private and transparent" do
194
+ context "when space is published and transparent" do
187
195
  let(:process_space_factory) { :assembly }
188
196
  let(:space_type) { "assembly" }
189
197
 
@@ -203,7 +211,7 @@ shared_examples "with resource visibility" do
203
211
  }
204
212
  )
205
213
  end
206
- let!(:participatory_process) { create(process_space_factory, :published, :private, :transparent, organization: current_organization) }
214
+ let!(:participatory_process) { create(process_space_factory, :published, :transparent, organization: current_organization) }
207
215
 
208
216
  context "when component is published" do
209
217
  let!(:current_component) { create(component_factory, :published, participatory_space: participatory_process) }
@@ -241,7 +249,7 @@ shared_examples "with resource visibility" do
241
249
 
242
250
  context "when user is member" do
243
251
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
244
- let!(:participatory_space_private_user) { create(:assembly_private_user, user: current_user, privatable_to: participatory_process) }
252
+ let!(:member) { create(:assembly_member, user: current_user, participatory_space: participatory_process) }
245
253
  it_behaves_like "graphQL visible resource"
246
254
  end
247
255
 
@@ -259,13 +267,13 @@ shared_examples "with resource visibility" do
259
267
  context "when the user is space admin" do
260
268
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
261
269
  let!(:role) { create(:assembly_user_role, assembly: participatory_process, user: current_user, role: "admin") }
262
- it_behaves_like "graphQL visible resource"
270
+ it_behaves_like "graphQL visible resource", visible: false
263
271
  end
264
272
 
265
273
  context "when the user is space collaborator" do
266
274
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
267
275
  let!(:role) { create(:assembly_user_role, assembly: participatory_process, user: current_user, role: "collaborator") }
268
- it_behaves_like "graphQL visible resource"
276
+ it_behaves_like "graphQL visible resource", visible: false
269
277
  end
270
278
 
271
279
  context "when the user is space moderator" do
@@ -277,7 +285,7 @@ shared_examples "with resource visibility" do
277
285
  context "when the user is space evaluator" do
278
286
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
279
287
  let!(:role) { create(:assembly_user_role, assembly: participatory_process, user: current_user, role: "evaluator") }
280
- it_behaves_like "graphQL visible resource"
288
+ it_behaves_like "graphQL visible resource", visible: false
281
289
  end
282
290
 
283
291
  context "when user is visitor" do
@@ -292,14 +300,14 @@ shared_examples "with resource visibility" do
292
300
 
293
301
  context "when user is member" do
294
302
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
295
- let!(:participatory_space_private_user) { create(:assembly_private_user, user: current_user, privatable_to: participatory_process) }
303
+ let!(:member) { create(:assembly_member, user: current_user, participatory_space: participatory_process) }
296
304
  it_behaves_like "graphQL hidden component"
297
305
  end
298
306
  end
299
307
  end
300
308
 
301
- context "when space is published but private" do
302
- let!(:participatory_process) { create(process_space_factory, :published, :private, :with_steps, organization: current_organization) }
309
+ context "when space is published but restricted" do
310
+ let!(:participatory_process) { create(process_space_factory, :published, :restricted, :with_steps, organization: current_organization) }
303
311
 
304
312
  context "when component is published" do
305
313
  let!(:current_component) { create(component_factory, :published, participatory_space: participatory_process) }
@@ -309,38 +317,38 @@ shared_examples "with resource visibility" do
309
317
  context "when the user is space admin" do
310
318
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
311
319
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "admin") }
312
- it_behaves_like "graphQL hidden space"
320
+ it_behaves_like "graphQL not found space"
313
321
  end
314
322
 
315
323
  context "when the user is space collaborator" do
316
324
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
317
325
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "collaborator") }
318
- it_behaves_like "graphQL hidden space"
326
+ it_behaves_like "graphQL not found space"
319
327
  end
320
328
 
321
329
  context "when the user is space moderator" do
322
330
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
323
331
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "moderator") }
324
332
 
325
- it_behaves_like "graphQL hidden space"
333
+ it_behaves_like "graphQL not found space"
326
334
  end
327
335
 
328
336
  context "when the user is space evaluator" do
329
337
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
330
338
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "evaluator") }
331
- it_behaves_like "graphQL hidden space"
339
+ it_behaves_like "graphQL not found space"
332
340
  end
333
341
 
334
342
  it_behaves_like "graphQL space hidden to visitor"
335
343
 
336
344
  context "when user is normal user" do
337
345
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
338
- it_behaves_like "graphQL hidden space"
346
+ it_behaves_like "graphQL not found space"
339
347
  end
340
348
 
341
349
  context "when user is member" do
342
350
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
343
- let!(:participatory_space_private_user) { create(:participatory_space_private_user, user: current_user, privatable_to: participatory_process) }
351
+ let!(:member) { create(:member, user: current_user, participatory_space: participatory_process) }
344
352
  it_behaves_like "graphQL visible resource"
345
353
  end
346
354
  end
@@ -353,36 +361,36 @@ shared_examples "with resource visibility" do
353
361
  context "when the user is space admin" do
354
362
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
355
363
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "admin") }
356
- it_behaves_like "graphQL hidden space"
364
+ it_behaves_like "graphQL not found space"
357
365
  end
358
366
 
359
367
  context "when the user is space collaborator" do
360
368
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
361
369
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "collaborator") }
362
- it_behaves_like "graphQL hidden space"
370
+ it_behaves_like "graphQL not found space"
363
371
  end
364
372
 
365
373
  context "when the user is space moderator" do
366
374
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
367
375
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "moderator") }
368
- it_behaves_like "graphQL hidden space"
376
+ it_behaves_like "graphQL not found space"
369
377
  end
370
378
 
371
379
  context "when the user is space evaluator" do
372
380
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
373
381
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "evaluator") }
374
- it_behaves_like "graphQL hidden space"
382
+ it_behaves_like "graphQL not found space"
375
383
  end
376
384
  it_behaves_like "graphQL space hidden to visitor"
377
385
 
378
386
  context "when user is member" do
379
387
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
380
- let!(:participatory_space_private_user) { create(:participatory_space_private_user, user: current_user, privatable_to: participatory_process) }
388
+ let!(:member) { create(:member, user: current_user, participatory_space: participatory_process) }
381
389
  it_behaves_like "graphQL hidden component"
382
390
  end
383
391
  context "when user is normal user" do
384
392
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
385
- it_behaves_like "graphQL hidden space"
393
+ it_behaves_like "graphQL not found space"
386
394
  end
387
395
  end
388
396
  end
@@ -398,38 +406,38 @@ shared_examples "with resource visibility" do
398
406
  context "when the user is space admin" do
399
407
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
400
408
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "admin") }
401
- it_behaves_like "graphQL hidden space"
409
+ it_behaves_like "graphQL not found space"
402
410
  end
403
411
 
404
412
  context "when the user is space collaborator" do
405
413
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
406
414
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "collaborator") }
407
- it_behaves_like "graphQL hidden space"
415
+ it_behaves_like "graphQL not found space"
408
416
  end
409
417
 
410
418
  context "when the user is space moderator" do
411
419
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
412
420
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "moderator") }
413
- it_behaves_like "graphQL hidden space"
421
+ it_behaves_like "graphQL not found space"
414
422
  end
415
423
 
416
424
  context "when the user is space evaluator" do
417
425
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
418
426
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "evaluator") }
419
- it_behaves_like "graphQL hidden space"
427
+ it_behaves_like "graphQL not found space"
420
428
  end
421
429
 
422
430
  it_behaves_like "graphQL space hidden to visitor"
423
431
 
424
432
  context "when user is member" do
425
433
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
426
- let!(:participatory_space_private_user) { create(:participatory_space_private_user, user: current_user, privatable_to: participatory_process) }
427
- it_behaves_like "graphQL hidden space"
434
+ let!(:member) { create(:member, user: current_user, participatory_space: participatory_process) }
435
+ it_behaves_like "graphQL not found space"
428
436
  end
429
437
 
430
438
  context "when user is normal user" do
431
439
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
432
- it_behaves_like "graphQL hidden space"
440
+ it_behaves_like "graphQL not found space"
433
441
  end
434
442
  end
435
443
 
@@ -441,38 +449,38 @@ shared_examples "with resource visibility" do
441
449
  context "when the user is space admin" do
442
450
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
443
451
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "admin") }
444
- it_behaves_like "graphQL hidden space"
452
+ it_behaves_like "graphQL not found space"
445
453
  end
446
454
 
447
455
  context "when the user is space collaborator" do
448
456
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
449
457
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "collaborator") }
450
- it_behaves_like "graphQL hidden space"
458
+ it_behaves_like "graphQL not found space"
451
459
  end
452
460
 
453
461
  context "when the user is space moderator" do
454
462
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
455
463
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "moderator") }
456
- it_behaves_like "graphQL hidden space"
464
+ it_behaves_like "graphQL not found space"
457
465
  end
458
466
 
459
467
  context "when the user is space evaluator" do
460
468
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
461
469
  let!(:role) { create(:participatory_process_user_role, participatory_process:, user: current_user, role: "evaluator") }
462
- it_behaves_like "graphQL hidden space"
470
+ it_behaves_like "graphQL not found space"
463
471
  end
464
472
  it_behaves_like "graphQL space hidden to visitor"
465
473
 
466
474
  context "when user is member" do
467
475
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
468
- let!(:participatory_space_private_user) { create(:participatory_space_private_user, user: current_user, privatable_to: participatory_process) }
469
- it_behaves_like "graphQL hidden space"
476
+ let!(:member) { create(:member, user: current_user, participatory_space: participatory_process) }
477
+ it_behaves_like "graphQL not found space"
470
478
  end
471
479
 
472
480
  context "when user is normal user" do
473
481
  let!(:current_user) { create(:user, :confirmed, organization: current_organization) }
474
482
 
475
- it_behaves_like "graphQL hidden space"
483
+ it_behaves_like "graphQL not found space"
476
484
  end
477
485
  end
478
486
  end
@@ -10,4 +10,50 @@ shared_examples_for "commentable interface" do
10
10
  expect(response["totalCommentsCount"]).to eq(model.comments_count)
11
11
  end
12
12
  end
13
+
14
+ describe "with comments" do
15
+ let(:comments) { create_list(:comment, 5, commentable: model) }
16
+ let(:subcomments_level1) do
17
+ comments.map do |comment|
18
+ create_list(:comment, 2, commentable: comment)
19
+ end.flatten
20
+ end
21
+ let!(:subcomments_level2) do
22
+ subcomments_level1.map do |comment|
23
+ create(:comment, commentable: comment)
24
+ end
25
+ end
26
+
27
+ let(:query) do
28
+ %(
29
+ {
30
+ comments {
31
+ ...dataFragment
32
+ comments {
33
+ ...dataFragment
34
+ }
35
+ }
36
+ }
37
+ fragment dataFragment on Comment {
38
+ id
39
+ body
40
+ createdAt
41
+ author { name }
42
+ }
43
+ )
44
+ end
45
+
46
+ it "includes the comments" do
47
+ expect(response["comments"]).to be_a(Array)
48
+ expect(response["comments"].count).to eq(5)
49
+
50
+ response["comments"].each do |comment|
51
+ expect(comment["comments"]).to be_a(Array)
52
+ expect(comment["comments"].count).to eq(2)
53
+
54
+ subcomments = subcomments_level1.select { |c| c.commentable.id == comment["id"].to_i }
55
+ expect(comment["comments"].map { |c| c["id"].to_i }).to match_array(subcomments.map(&:id))
56
+ end
57
+ end
58
+ end
13
59
  end
@@ -4,10 +4,21 @@ require "spec_helper"
4
4
 
5
5
  shared_examples_for "followable interface" do
6
6
  describe "follows_count" do
7
+ let!(:follow) { create(:follow, followable: model) }
7
8
  let(:query) { "{ followsCount }" }
8
9
 
9
10
  it "includes the field" do
10
- expect(response["followsCount"]).to eq(model.follows_count)
11
+ expect(response["followsCount"]).to eq(model.reload.follows_count)
12
+ end
13
+ end
14
+
15
+ describe "followers" do
16
+ let!(:follow) { create(:follow, followable: model) }
17
+ let(:query) { "{ followers { id } }" }
18
+
19
+ it "includes the field" do
20
+ expect(response["followers"]).to be_present
21
+ expect(response["followers"]).to include({ "id" => model.reload.followers.first.id.to_s })
11
22
  end
12
23
  end
13
24
  end
@@ -15,7 +15,6 @@ shared_examples "implements stats type" do
15
15
  { name: "surveys_count", data: [0], tooltip_key: "surveys_count_tooltip" },
16
16
  { name: "results_count", data: [0], tooltip_key: "results_count_tooltip" },
17
17
  { name: "debates_count", data: [0], tooltip_key: "debates_count_tooltip" },
18
- { name: "sortitions_count", data: [0], tooltip_key: "sortitions_count_tooltip" },
19
18
  { name: "posts_count", data: [0], tooltip_key: "posts_count_tooltip" },
20
19
  { name: "collaborative_texts_count", data: [0], tooltip_key: "collaborative_texts_count_tooltip" }
21
20
  ]))
@@ -36,7 +35,6 @@ shared_examples "implements stats type" do
36
35
  { "name" => { "translation" => "Surveys" }, "value" => 0 },
37
36
  { "name" => { "translation" => "Results" }, "value" => 0 },
38
37
  { "name" => { "translation" => "Debates" }, "value" => 0 },
39
- { "name" => { "translation" => "Sortitions" }, "value" => 0 },
40
38
  { "name" => { "translation" => "Posts" }, "value" => 0 },
41
39
  { "name" => { "translation" => "Collaborative texts" }, "value" => 0 }
42
40
  ]
@@ -35,8 +35,17 @@ shared_context "with a graphql class type" do
35
35
  # Matches the error code with the Error class
36
36
  # For instance, if the error code is NOT_FOUND_ERROR then it will raise the "Decidim::Api::Errors::NotFoundError" class
37
37
  raise "Decidim::Api::Errors::#{code.downcase.classify}".constantize, error["message"] if %w(
38
- INTROSPECTION_DISABLED_ERROR
38
+ LOCALE_ERROR
39
+ NOT_FOUND_ERROR
40
+ INVALID_LOCALE_ERROR
41
+ PERMISSION_NOT_SET_ERROR
42
+ ATTRIBUTE_VALIDATION_ERROR
43
+ UNAUTHORIZED_FIELD_ERROR
44
+ UNAUTHORIZED_OBJECT_ERROR
45
+ MUTATION_NOT_AUTHORIZED_ERROR
46
+ VALIDATION_ERROR
39
47
  TOO_MANY_ALIASES_ERROR
48
+ INTROSPECTION_DISABLED_ERROR
40
49
  RECURSION_LIMIT_EXCEEDED_ERROR
41
50
  ).include?(code)
42
51
 
@@ -103,7 +112,6 @@ shared_examples "when the introspection is disabled" do
103
112
  before do
104
113
  allow(Decidim::Api).to receive(:enable_anonymous_introspection).and_return(false)
105
114
  end
106
-
107
115
  it "raises an Decidim::Api::Errors::IntrospectionDisabledError" do
108
116
  expect { response }.to raise_error(Decidim::Api::Errors::IntrospectionDisabledError, "Introspection is disabled for this request")
109
117
  end
@@ -22,4 +22,5 @@ require "decidim/api/test/shared_examples/statistics_examples"
22
22
  require "decidim/api/test/shared_examples/taxonomizable_interface_examples"
23
23
  require "decidim/api/test/shared_examples/timestamps_interface_examples"
24
24
  require "decidim/api/test/shared_examples/traceable_interface_examples"
25
+ require "decidim/api/test/shared_examples/mutation_context"
25
26
  require "decidim/api/test/type_context"
@@ -0,0 +1,15 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Decidim
4
+ module Api
5
+ module Types
6
+ class AccessModeEnum < Decidim::Api::Types::BaseEnum
7
+ description "The access modes for participatory spaces"
8
+
9
+ value "OPEN", value: "open", description: "Open to everyone"
10
+ value "TRANSPARENT", value: "transparent", description: "Transparent (visible but restricted participation)"
11
+ value "RESTRICTED", value: "restricted", description: "Restricted to members only"
12
+ end
13
+ end
14
+ end
15
+ end
@@ -5,12 +5,40 @@ module Decidim
5
5
  module Types
6
6
  class BaseMutation < GraphQL::Schema::RelayClassicMutation
7
7
  include Decidim::Api::GraphqlPermissions
8
+ include Decidim::FormFactory
8
9
 
9
10
  object_class BaseObject
10
11
  field_class Types::BaseField
11
12
  input_object_class BaseInputObject
12
13
 
13
14
  required_scopes "api:read", "api:write"
15
+
16
+ def set_locale(locale:, toggle_translations:)
17
+ raise I18n::InvalidLocale, "#{locale} is not a valid locale" unless available_locales.include?(locale)
18
+
19
+ I18n.locale = locale.presence
20
+ RequestStore.store[:toggle_machine_translations] = toggle_translations
21
+ end
22
+
23
+ def current_user
24
+ context[:current_user]
25
+ end
26
+
27
+ def current_component
28
+ context[:current_component]
29
+ end
30
+
31
+ def current_organization
32
+ context[:current_organization]
33
+ end
34
+
35
+ def available_locales
36
+ if current_organization.present?
37
+ current_organization.available_locales
38
+ else
39
+ I18n.available_locales.map(&:to_s)
40
+ end
41
+ end
14
42
  end
15
43
  end
16
44
  end
@@ -10,6 +10,18 @@ module Decidim
10
10
  field_class Types::BaseField
11
11
 
12
12
  required_scopes "api:read"
13
+
14
+ def current_user
15
+ context[:current_user]
16
+ end
17
+
18
+ def current_component
19
+ context[:current_component]
20
+ end
21
+
22
+ def current_organization
23
+ context[:current_organization]
24
+ end
13
25
  end
14
26
  end
15
27
  end
@@ -2,9 +2,9 @@
2
2
 
3
3
  module Decidim
4
4
  module Api
5
- autoload :RecursionAnalyzer, "decidim/api/recursion_analyzer"
6
5
  autoload :IntrospectionAnalyzer, "decidim/api/introspection_analyzer"
7
6
  autoload :AliasAnalyzer, "decidim/api/alias_analyzer"
7
+ autoload :RecursionAnalyzer, "decidim/api/recursion_analyzer"
8
8
  autoload :QueryType, "decidim/api/query_type"
9
9
  autoload :MutationType, "decidim/api/mutation_type"
10
10
  autoload :Schema, "decidim/api/schema"
@@ -14,7 +14,16 @@ module Decidim
14
14
 
15
15
  module Errors
16
16
  autoload :IntrospectionDisabledError, "decidim/api/errors/introspection_disabled_error"
17
+ autoload :LocaleError, "decidim/api/errors/locale_error"
17
18
  autoload :TooManyAliasesError, "decidim/api/errors/too_many_aliases_error"
19
+ autoload :InvalidLocaleError, "decidim/api/errors/invalid_locale_error"
20
+ autoload :AttributeValidationError, "decidim/api/errors/attribute_validation_error"
21
+ autoload :MutationNotAuthorizedError, "decidim/api/errors/mutation_not_authorized_error"
22
+ autoload :NotFoundError, "decidim/api/errors/not_found_error"
23
+ autoload :PermissionNotSetError, "decidim/api/errors/permission_not_set_error"
24
+ autoload :UnauthorizedFieldError, "decidim/api/errors/unauthorized_field_error"
25
+ autoload :UnauthorizedObjectError, "decidim/api/errors/unauthorized_object_error"
26
+ autoload :ValidationError, "decidim/api/errors/validation_error"
18
27
  autoload :RecursionLimitExceededError, "decidim/api/errors/recursion_limit_exceeded_error"
19
28
  end
20
29
 
@@ -28,6 +37,8 @@ module Decidim
28
37
  autoload :BaseObject, "decidim/api/types/base_object"
29
38
  autoload :BaseScalar, "decidim/api/types/base_scalar"
30
39
  autoload :BaseUnion, "decidim/api/types/base_union"
40
+
41
+ autoload :AccessModeEnum, "decidim/api/types/access_mode_enum"
31
42
  end
32
43
  end
33
44
  end
@@ -4,7 +4,7 @@ module Decidim
4
4
  # This holds the decidim-api version.
5
5
  module Api
6
6
  def self.version
7
- "0.31.4"
7
+ "0.32.0.rc1"
8
8
  end
9
9
  end
10
10
  end