notion 1.0.6 → 1.1.3

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,16 +1,16 @@
1
1
  module NotionAPI
2
2
 
3
- # good for just about anything (-:
4
- class TextBlock < BlockTemplate
5
- @notion_type = 'text'
6
- @type = 'text'
7
-
8
- def type
9
- NotionAPI::TextBlock.notion_type
10
- end
11
-
12
- class << self
13
- attr_reader :notion_type, :type
14
- end
3
+ # good for just about anything (-:
4
+ class TextBlock < BlockTemplate
5
+ @notion_type = "text"
6
+ @type = "text"
7
+
8
+ def type
9
+ NotionAPI::TextBlock.notion_type
10
+ end
11
+
12
+ class << self
13
+ attr_reader :notion_type, :type
15
14
  end
16
- end
15
+ end
16
+ end
@@ -1,60 +1,60 @@
1
1
  module NotionAPI
2
2
 
3
- # To-Do block: best for checklists and tracking to-dos.
4
- class TodoBlock < BlockTemplate
5
- @notion_type = 'to_do'
6
- @type = 'to_do'
7
-
8
- def type
9
- NotionAPI::TodoBlock.notion_type
10
- end
11
-
12
- class << self
13
- attr_reader :notion_type, :type
14
- end
15
-
16
- def checked=(checked_value)
17
- # ! change the checked property of the Todo Block.
18
- # ! checked_value -> boolean value used to determine whether the block should be checked [yes] or not [no] : ``str``
19
- # set static variables for request
20
- cookies = Core.options['cookies']
21
- headers = Core.options['headers']
22
- request_url = URLS[:UPDATE_BLOCK]
23
-
24
- # set unique values for request
25
- request_id = extract_id(SecureRandom.hex(16))
26
- transaction_id = extract_id(SecureRandom.hex(16))
27
- space_id = extract_id(SecureRandom.hex(16))
28
- request_ids = {
29
- request_id: request_id,
30
- transaction_id: transaction_id,
31
- space_id: space_id
32
- }
33
-
34
- if %w[yes no].include?(checked_value.downcase)
35
- checked_hash = Utils::BlockComponents.checked_todo(@id, checked_value.downcase)
36
- last_edited_time_parent_hash = Utils::BlockComponents.last_edited_time(@parent_id)
37
- last_edited_time_child_hash = Utils::BlockComponents.last_edited_time(@id)
38
-
39
- operations = [
40
- checked_hash,
41
- last_edited_time_parent_hash,
42
- last_edited_time_child_hash
43
- ]
44
- request_body = build_payload(operations, request_ids)
45
- response = HTTParty.post(
46
- request_url,
47
- body: request_body.to_json,
48
- cookies: cookies,
49
- headers: headers
50
- )
51
- unless response.code == 200; raise "There was an issue completing your request. Here is the response from Notion: #{response.body}, and here is the payload that was sent: #{operations}.
52
- Please try again, and if issues persist open an issue in GitHub."; end
53
-
54
- true
55
- else
56
- false
57
- end
3
+ # To-Do block: best for checklists and tracking to-dos.
4
+ class TodoBlock < BlockTemplate
5
+ @notion_type = "to_do"
6
+ @type = "to_do"
7
+
8
+ def type
9
+ NotionAPI::TodoBlock.notion_type
10
+ end
11
+
12
+ class << self
13
+ attr_reader :notion_type, :type
14
+ end
15
+
16
+ def checked=(checked_value)
17
+ # ! change the checked property of the Todo Block.
18
+ # ! checked_value -> boolean value used to determine whether the block should be checked [yes] or not [no] : ``str``
19
+ # set static variables for request
20
+ cookies = Core.options["cookies"]
21
+ headers = Core.options["headers"]
22
+ request_url = URLS[:UPDATE_BLOCK]
23
+
24
+ # set unique values for request
25
+ request_id = extract_id(SecureRandom.hex(16))
26
+ transaction_id = extract_id(SecureRandom.hex(16))
27
+ space_id = extract_id(SecureRandom.hex(16))
28
+ request_ids = {
29
+ request_id: request_id,
30
+ transaction_id: transaction_id,
31
+ space_id: space_id,
32
+ }
33
+
34
+ if %w[yes no].include?(checked_value.downcase)
35
+ checked_hash = Utils::BlockComponents.checked_todo(@id, checked_value.downcase)
36
+ last_edited_time_parent_hash = Utils::BlockComponents.last_edited_time(@parent_id)
37
+ last_edited_time_child_hash = Utils::BlockComponents.last_edited_time(@id)
38
+
39
+ operations = [
40
+ checked_hash,
41
+ last_edited_time_parent_hash,
42
+ last_edited_time_child_hash,
43
+ ]
44
+ request_body = build_payload(operations, request_ids)
45
+ response = HTTParty.post(
46
+ request_url,
47
+ body: request_body.to_json,
48
+ cookies: cookies,
49
+ headers: headers,
50
+ )
51
+ unless response.code == 200; raise "There was an issue completing your request. Here is the response from Notion: #{response.body}, and here is the payload that was sent: #{operations}.
52
+ Please try again, and if issues persist open an issue in GitHub."; end
53
+
54
+ true
55
+ else
56
+ false
58
57
  end
59
58
  end
60
- end
59
+ end
60
+ end
@@ -1,16 +1,16 @@
1
1
  module NotionAPI
2
2
 
3
- # Toggle block: best for storing children blocks
4
- class ToggleBlock < BlockTemplate
5
- @notion_type = 'toggle'
6
- @type = 'toggle'
7
-
8
- def type
9
- NotionAPI::ToggleBlock.notion_type
10
- end
11
-
12
- class << self
13
- attr_reader :notion_type, :type
14
- end
3
+ # Toggle block: best for storing children blocks
4
+ class ToggleBlock < BlockTemplate
5
+ @notion_type = "toggle"
6
+ @type = "toggle"
7
+
8
+ def type
9
+ NotionAPI::ToggleBlock.notion_type
10
+ end
11
+
12
+ class << self
13
+ attr_reader :notion_type, :type
15
14
  end
16
- end
15
+ end
16
+ end
@@ -11,6 +11,27 @@ module Utils
11
11
  class BlockComponents
12
12
  # ! Each function defined here builds one component that is included in each request sent to Notions backend.
13
13
  # ! Each request sent will contain multiple components.
14
+ # TODO figure this out
15
+ def self.build_payload(operations, request_ids)
16
+ # ! properly formats the payload for Notions backend.
17
+ # ! operations -> an array of hashes that define the operations to perform : ``Array[Hash]``
18
+ # ! request_ids -> the unique IDs for the request : ``str``
19
+ request_id = request_ids[:request_id]
20
+ transaction_id = request_ids[:transaction_id]
21
+ space_id = request_ids[:space_id]
22
+ payload = {
23
+ requestId: request_id,
24
+ transactions: [
25
+ {
26
+ id: transaction_id,
27
+ shardId: 955_090,
28
+ spaceId: space_id,
29
+ operations: operations,
30
+ },
31
+ ],
32
+ }
33
+ payload
34
+ end
14
35
  def self.create(block_id, block_type)
15
36
  # ! payload for creating a block.
16
37
  # ! block_id -> id of the new block : ``str``
@@ -200,14 +221,14 @@ module Utils
200
221
 
201
222
  args = if command == "listAfter"
202
223
  {
203
- after: target || block_id,
204
- id: new_block_id || block_id,
205
- }
224
+ after: target || block_id,
225
+ id: new_block_id || block_id,
226
+ }
206
227
  else
207
228
  {
208
- before: target || block_id,
209
- id: new_block_id || block_id,
210
- }
229
+ before: target || block_id,
230
+ id: new_block_id || block_id,
231
+ }
211
232
  end
212
233
 
213
234
  {
@@ -219,6 +240,25 @@ module Utils
219
240
  }
220
241
  end
221
242
 
243
+ def self.row_location_add(last_row_id, block_id, view_id)
244
+ # ! add a new row to a Collection View table
245
+ # ! last_row_id -> ID of the last row in the CV : ``str``
246
+ # ! block_id -> ID of the blow : ``str``
247
+ # ! view_id -> ID of the View : ``str``
248
+ {
249
+ "table": "collection_view",
250
+ "id": view_id,
251
+ "path": [
252
+ "page_sort",
253
+ ],
254
+ "command": "listAfter",
255
+ "args": {
256
+ "after": last_row_id,
257
+ "id": block_id,
258
+ },
259
+ }
260
+ end
261
+
222
262
  def self.block_location_remove(block_parent_id, block_id)
223
263
  # ! removes a notion block
224
264
  # ! block_parent_id -> the parent ID of the block to remove : ``str``
@@ -274,11 +314,52 @@ module Utils
274
314
  }
275
315
  end
276
316
  def self.add_emoji_icon(block_id, icon)
317
+ # ! add an emoji icon for either a page or callout block
318
+ # ! block_id -> the ID of the block : ``str``
319
+ # ! icon -> the icon for the block. This is currently randomly chosen. : ``str``
277
320
  {
278
321
  id: block_id,
279
- table:"block",
280
- path:["format","page_icon"],
281
- command:"set","args": icon
322
+ table: "block",
323
+ path: ["format", "page_icon"],
324
+ command: "set", "args": icon,
325
+ }
326
+ end
327
+
328
+ def self.source(new_block_id, url)
329
+ # ! set the source for the ImageBlock
330
+ # ! new_block_id -> the ID of the new ImageBlock: ``str``
331
+ # ! url -> the URL for the image
332
+ table = "block"
333
+ path = ["properties"]
334
+ command = "update"
335
+
336
+ {
337
+ id: new_block_id,
338
+ table: table,
339
+ path: path,
340
+ command: command,
341
+ args: {
342
+ source: [[
343
+ url,
344
+ ]],
345
+ },
346
+ }
347
+ end
348
+
349
+ def self.display_source(new_block_id, block_url)
350
+ # ! set the display source for the ImageBlock
351
+ # ! new_block_id -> the ID of the new ImageBlock: ``str``
352
+ # ! block_url -> the URL of the ImageBlock: ``str``
353
+ {
354
+ "id": new_block_id,
355
+ "table": "block",
356
+ "path": [
357
+ "format",
358
+ ],
359
+ "command": "update",
360
+ "args": {
361
+ "display_source": block_url,
362
+ },
282
363
  }
283
364
  end
284
365
  end
@@ -383,14 +464,14 @@ module Utils
383
464
  # ! new_block_id -> id of the new block
384
465
  # ! data -> json data to insert into table.
385
466
  col_names = data[0].keys
386
- data_mappings = {Integer => "number", String => "text", Array => "text", Float => "number", Date => "date"}
467
+ data_mappings = { Integer => "number", String => "text", Array => "text", Float => "number", Date => "date" }
387
468
  exceptions = [ArgumentError, TypeError]
388
469
  data_types = col_names.map do |name|
389
470
  # TODO: this is a little hacky... should probably think about a better way or add a requirement for user input to match a certain criteria.
390
- begin
471
+ begin
391
472
  DateTime.parse(data[0][name]) ? data_mappings[Date] : nil
392
473
  rescue *exceptions
393
- data_mappings[data[0][name].class]
474
+ data_mappings[data[0][name].class]
394
475
  end
395
476
  end
396
477
 
@@ -403,18 +484,18 @@ module Utils
403
484
  end
404
485
  end
405
486
  return {
406
- id: collection_id,
407
- table: "collection",
408
- path: [],
409
- command: "update",
410
- args: {
411
- id: collection_id,
412
- schema: schema_conf,
413
- parent_id: new_block_id,
414
- parent_table: "block",
415
- alive: true,
416
- },
417
- }, data_types
487
+ id: collection_id,
488
+ table: "collection",
489
+ path: [],
490
+ command: "update",
491
+ args: {
492
+ id: collection_id,
493
+ schema: schema_conf,
494
+ parent_id: new_block_id,
495
+ parent_table: "block",
496
+ alive: true,
497
+ },
498
+ }, data_types
418
499
  end
419
500
 
420
501
  def self.set_collection_title(collection_title, collection_id)
@@ -440,6 +521,12 @@ module Utils
440
521
  # ! column -> the name of the column to insert data into.
441
522
  # ! value -> the value to insert into the column.
442
523
  # ! mapping -> the column data type.
524
+ simple_mappings = ["title", "text", "phone_number", "email", "url", "number", "checkbox", "select", "multi_select"]
525
+ datetime_mappings = ["date"]
526
+ media_mappings = ["file"]
527
+ person_mappings = ["person"]
528
+ page_mappings = ["relation"]
529
+
443
530
  table = "block"
444
531
  path = [
445
532
  "properties",
@@ -447,12 +534,52 @@ module Utils
447
534
  ]
448
535
  command = "set"
449
536
 
537
+ if simple_mappings.include?(mapping)
538
+ args = [[value]]
539
+ elsif media_mappings.include?(mapping)
540
+ args = [[value, [["a", value]]]]
541
+ elsif datetime_mappings.include?(mapping)
542
+ args = [["‣", [["d", { "type": "date", "start_date": value }]]]]
543
+ elsif person_mappings.include?(mapping)
544
+ args = [["‣",
545
+ [["u", value]]]]
546
+ elsif page_mappings.include?(mapping)
547
+ args = [["‣",
548
+ [["p", value]]]]
549
+ else
550
+ raise SchemaTypeError, "Invalid property type: #{mapping}"
551
+ end
552
+
450
553
  {
451
- id: block_id,
452
554
  table: table,
555
+ id: block_id,
556
+ command: command,
453
557
  path: path,
558
+ args: args,
559
+ }
560
+ end
561
+
562
+ def self.add_new_option(column, value, collection_id)
563
+ table = "collection"
564
+ path = ["schema", column, "options"]
565
+ command = "keyedObjectListAfter"
566
+ colors = ["default", "gray", "brown", "orange", "yellow", "green", "blue", "purple", "pink", "red"]
567
+ random_color = colors[rand(0...colors.length)]
568
+
569
+ args = {
570
+ "value": {
571
+ "id": SecureRandom.hex(16),
572
+ "value": value,
573
+ "color": random_color,
574
+ },
575
+ }
576
+
577
+ {
578
+ table: table,
579
+ id: collection_id,
454
580
  command: command,
455
- args: mapping == "date" ? [["‣",[["d",{"type": "date","start_date": value}]]]] : [[value]],
581
+ path: path,
582
+ args: args,
456
583
  }
457
584
  end
458
585
 
@@ -502,50 +629,7 @@ module Utils
502
629
  # ! payload for adding a column to the table.
503
630
  # ! collection_id -> the collection ID : ``str``
504
631
  # ! args -> the definition of the column : ``str``
505
- args["format"] = {
506
- "table_properties" => [
507
- {
508
- "property" => "title",
509
- "visible" => true,
510
- "width" => 280,
511
- },
512
- {
513
- "property" => "aliases",
514
- "visible" => true,
515
- "width" => 200,
516
- },
517
- {
518
- "property" => "category",
519
- "visible" => true,
520
- "width" => 200,
521
- },
522
- {
523
- "property" => "description",
524
- "visible" => true,
525
- "width" => 200,
526
- },
527
- {
528
- "property" => "ios_version",
529
- "visible" => true,
530
- "width" => 200,
531
- },
532
- {
533
- "property" => "tags",
534
- "visible" => true,
535
- "width" => 200,
536
- },
537
- {
538
- "property" => "phone",
539
- "visible" => true,
540
- "width" => 200,
541
- },
542
- {
543
- "property" => "unicode_version",
544
- "visible" => true,
545
- "width" => 200,
546
- }
547
- ],
548
- }
632
+
549
633
  {
550
634
  id: collection_id,
551
635
  table: "collection",
@@ -555,31 +639,46 @@ module Utils
555
639
  }
556
640
  end
557
641
 
558
- def self.update_property_value(page_id, column_name, new_value)
642
+ def self.update_property_value(page_id, column_name, new_value, column_type)
559
643
  # ! update the specified column_name to new_value
560
644
  # ! page_id -> the ID of the page: ``str``
561
645
  # ! column_name -> the name of the column ["property"] to update: ``str``
562
646
  # ! new_value -> the new value to assign to that column ["property"]: ``str``
647
+ # ! column_type -> the type of the property: ``str``
563
648
  table = "block"
564
649
  path = [
565
650
  "properties",
566
- column_name
651
+ column_name,
567
652
  ]
568
653
  command = "set"
569
- args = [[
570
- new_value
571
- ]]
654
+
655
+ if column_type == "relation"
656
+ args = [["‣", [[
657
+ "p", new_value,
658
+ ]]]]
659
+ else
660
+ args = [[
661
+ new_value,
662
+ ]]
663
+ end
572
664
 
573
665
  {
574
666
  id: page_id,
575
667
  table: table,
576
668
  path: path,
577
669
  command: command,
578
- args: args
670
+ args: args,
579
671
  }
580
672
  end
581
673
  end
582
674
 
675
+ class SchemaTypeError < StandardError
676
+ def initialize(msg = "Custom exception that is raised when an invalid property type is passed as a mapping.", exception_type = "schema_type")
677
+ @exception_type = exception_type
678
+ super(msg)
679
+ end
680
+ end
681
+
583
682
  def build_payload(operations, request_ids)
584
683
  # ! properly formats the payload for Notions backend.
585
684
  # ! operations -> an array of hashes that define the operations to perform : ``Array[Hash]``