primitive 0.1.58__py3-none-any.whl → 0.1.60__py3-none-any.whl

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 (68) hide show
  1. primitive/__about__.py +1 -1
  2. primitive/agent/__init__.py +0 -0
  3. primitive/agent/actions.py +8 -4
  4. primitive/agent/process.py +2 -2
  5. primitive/agent/provision.py +2 -8
  6. primitive/agent/runner.py +22 -12
  7. primitive/agent/uploader.py +78 -49
  8. primitive/auth/actions.py +5 -12
  9. primitive/auth/graphql/__init__.py +0 -0
  10. primitive/auth/graphql/queries.py +13 -0
  11. primitive/cli.py +11 -5
  12. primitive/client.py +4 -0
  13. primitive/daemons/__init__.py +0 -0
  14. primitive/exec/__init__.py +0 -0
  15. primitive/exec/actions.py +50 -0
  16. primitive/exec/commands.py +22 -0
  17. primitive/files/__init__.py +0 -0
  18. primitive/files/actions.py +9 -16
  19. primitive/files/graphql/__init__.py +0 -0
  20. primitive/files/graphql/mutations.py +11 -0
  21. primitive/git/actions.py +11 -11
  22. primitive/git/commands.py +7 -6
  23. primitive/git/graphql/__init__.py +0 -0
  24. primitive/git/graphql/queries.py +7 -0
  25. primitive/graphql/relay.py +32 -0
  26. primitive/graphql/utility_fragments.py +19 -0
  27. primitive/hardware/__init__.py +0 -0
  28. primitive/hardware/actions.py +74 -121
  29. primitive/hardware/commands.py +15 -5
  30. primitive/hardware/graphql/__init__.py +0 -0
  31. primitive/hardware/graphql/fragments.py +22 -0
  32. primitive/hardware/graphql/mutations.py +45 -0
  33. primitive/hardware/graphql/queries.py +31 -0
  34. primitive/jobs/__init__.py +0 -0
  35. primitive/jobs/actions.py +32 -201
  36. primitive/jobs/graphql/__init__.py +0 -0
  37. primitive/jobs/graphql/fragments.py +47 -0
  38. primitive/jobs/graphql/mutations.py +11 -0
  39. primitive/jobs/graphql/queries.py +100 -0
  40. primitive/lint/__init__.py +0 -0
  41. primitive/organizations/__init__.py +0 -0
  42. primitive/organizations/actions.py +4 -49
  43. primitive/organizations/graphql/__init__.py +0 -0
  44. primitive/organizations/graphql/fragments.py +10 -0
  45. primitive/organizations/graphql/mutations.py +0 -0
  46. primitive/organizations/graphql/queries.py +38 -0
  47. primitive/projects/actions.py +5 -47
  48. primitive/projects/graphql/__init__.py +0 -0
  49. primitive/projects/graphql/fragments.py +10 -0
  50. primitive/projects/graphql/mutations.py +0 -0
  51. primitive/projects/graphql/queries.py +36 -0
  52. primitive/reservations/__init__.py +0 -0
  53. primitive/reservations/actions.py +134 -0
  54. primitive/reservations/commands.py +67 -0
  55. primitive/reservations/graphql/__init__.py +0 -0
  56. primitive/reservations/graphql/fragments.py +40 -0
  57. primitive/reservations/graphql/mutations.py +29 -0
  58. primitive/reservations/graphql/queries.py +47 -0
  59. primitive/sim/actions.py +12 -9
  60. primitive/utils/__init__.py +0 -0
  61. primitive/utils/cache.py +14 -0
  62. primitive/utils/shell.py +25 -0
  63. {primitive-0.1.58.dist-info → primitive-0.1.60.dist-info}/METADATA +1 -1
  64. primitive-0.1.60.dist-info/RECORD +95 -0
  65. primitive-0.1.58.dist-info/RECORD +0 -53
  66. {primitive-0.1.58.dist-info → primitive-0.1.60.dist-info}/WHEEL +0 -0
  67. {primitive-0.1.58.dist-info → primitive-0.1.60.dist-info}/entry_points.txt +0 -0
  68. {primitive-0.1.58.dist-info → primitive-0.1.60.dist-info}/licenses/LICENSE.txt +0 -0
@@ -0,0 +1,19 @@
1
+ operation_info_fragment = """
2
+ fragment OperationInfoFragment on OperationInfo {
3
+ messages {
4
+ kind
5
+ message
6
+ field
7
+ code
8
+ }
9
+ }
10
+ """
11
+
12
+ page_info_fragment = """
13
+ fragment PageInfoFragment on PageInfo {
14
+ hasNextPage
15
+ hasPreviousPage
16
+ startCursor
17
+ endCursor
18
+ }
19
+ """
File without changes
@@ -2,18 +2,27 @@ import csv
2
2
  import io
3
3
  import json
4
4
  import platform
5
- from shutil import which
6
5
  import subprocess
6
+ import typing
7
+ from shutil import which
7
8
  from typing import Dict, List, Optional
9
+
8
10
  import click
11
+ from aiohttp import client_exceptions
12
+ from gql import gql
9
13
  from loguru import logger
14
+
15
+ from primitive.graphql.relay import from_base64
10
16
  from primitive.utils.memory_size import MemorySize
11
- from gql import gql
12
- from aiohttp import client_exceptions
13
- from ..utils.config import update_config_file
14
- from ..utils.auth import guard
15
17
 
16
- import typing
18
+ from ..utils.auth import guard
19
+ from ..utils.config import update_config_file
20
+ from .graphql.mutations import (
21
+ hardware_checkin_mutation,
22
+ hardware_update_mutation,
23
+ register_hardware_mutation,
24
+ )
25
+ from .graphql.queries import hardware_list
17
26
 
18
27
  if typing.TYPE_CHECKING:
19
28
  pass
@@ -269,29 +278,13 @@ class Hardware(BaseAction):
269
278
  @guard
270
279
  def register(self):
271
280
  system_info = self.get_system_info()
272
- mutation = gql(
273
- """
274
- mutation registerHardware($input: RegisterHardwareInput!) {
275
- registerHardware(input: $input) {
276
- ... on Hardware {
277
- fingerprint
278
- }
279
- ... on OperationInfo {
280
- messages {
281
- kind
282
- message
283
- field
284
- code
285
- }
286
- }
287
- }
288
- }
289
- """
290
- )
281
+ mutation = gql(register_hardware_mutation)
291
282
  input = {"systemInfo": system_info}
292
283
  variables = {"input": input}
293
- result = self.primitive.session.execute(mutation, variable_values=variables)
294
- if messages := result.get("registerHardware").get("messages"):
284
+ result = self.primitive.session.execute(
285
+ mutation, variable_values=variables, get_execution_result=True
286
+ )
287
+ if messages := result.data.get("registerHardware").get("messages"):
295
288
  for message in messages:
296
289
  logger.enable("primitive")
297
290
  if message.get("kind") == "ERROR":
@@ -300,7 +293,7 @@ class Hardware(BaseAction):
300
293
  logger.debug(message.get("message"))
301
294
  return False
302
295
 
303
- fingerprint = result.get("registerHardware").get("fingerprint")
296
+ fingerprint = result.data.get("registerHardware").get("fingerprint")
304
297
 
305
298
  self.primitive.host_config["fingerprint"] = fingerprint
306
299
  self.primitive.full_config[self.primitive.host] = self.primitive.host_config
@@ -335,30 +328,14 @@ class Hardware(BaseAction):
335
328
  "systemInfo": system_info,
336
329
  }
337
330
 
338
- mutation = gql(
339
- """
340
- mutation hardwareUpdate($input: HardwareUpdateInput!) {
341
- hardwareUpdate(input: $input) {
342
- ... on Hardware {
343
- systemInfo
344
- }
345
- ... on OperationInfo {
346
- messages {
347
- kind
348
- message
349
- field
350
- code
351
- }
352
- }
353
- }
354
- }
355
- """
356
- )
331
+ mutation = gql(hardware_update_mutation)
357
332
 
358
333
  input = new_state
359
334
  variables = {"input": input}
360
335
  try:
361
- result = self.primitive.session.execute(mutation, variable_values=variables)
336
+ result = self.primitive.session.execute(
337
+ mutation, variable_values=variables, get_execution_result=True
338
+ )
362
339
  except client_exceptions.ClientConnectorError as exception:
363
340
  message = " [*] Failed to update hardware system info! "
364
341
  logger.error(message)
@@ -391,27 +368,7 @@ class Hardware(BaseAction):
391
368
  "isOnline": is_online,
392
369
  }
393
370
 
394
- mutation = gql(
395
- """
396
- mutation checkIn($input: CheckInInput!) {
397
- checkIn(input: $input) {
398
- ... on Hardware {
399
- createdAt
400
- updatedAt
401
- lastCheckIn
402
- }
403
- ... on OperationInfo {
404
- messages {
405
- kind
406
- message
407
- field
408
- code
409
- }
410
- }
411
- }
412
- }
413
- """ # noqa
414
- )
371
+ mutation = gql(hardware_checkin_mutation)
415
372
  input = new_state
416
373
  variables = {"input": input}
417
374
  try:
@@ -459,70 +416,66 @@ class Hardware(BaseAction):
459
416
  raise exception
460
417
 
461
418
  @guard
462
- def get_hardware_list(self, fingerprint: Optional[str] = None):
463
- query = gql(
464
- """
465
- fragment HardwareFragment on Hardware {
466
- id
467
- pk
468
- name
469
- slug
470
- createdAt
471
- updatedAt
472
- isAvailable
473
- isOnline
474
- isQuarantined
475
- isHealthy
476
- capabilities {
477
- id
478
- pk
479
- }
480
- activeReservation {
481
- id
482
- pk
483
- }
484
- }
485
-
486
- query hardwareList(
487
- $before: String
488
- $after: String
489
- $first: Int
490
- $last: Int
491
- $filters: HardwareFilters
492
- ) {
493
- hardwareList(
494
- before: $before
495
- after: $after
496
- first: $first
497
- last: $last
498
- filters: $filters
499
- ) {
500
- totalCount
501
- edges {
502
- cursor
503
- node {
504
- ...HardwareFragment
505
- }
506
- }
507
- }
508
- }
509
- """
510
- )
419
+ def get_hardware_list(
420
+ self, fingerprint: Optional[str] = None, slug: Optional[str] = None
421
+ ):
422
+ query = gql(hardware_list)
511
423
 
512
424
  filters = {}
513
425
  if fingerprint:
514
426
  filters["fingerprint"] = {"exact": fingerprint}
427
+ if slug:
428
+ filters["slug"] = {"exact": slug}
515
429
 
516
430
  variables = {
517
431
  "first": 1,
518
432
  "filters": filters,
519
433
  }
520
- result = self.primitive.session.execute(query, variable_values=variables)
434
+ result = self.primitive.session.execute(
435
+ query, variable_values=variables, get_execution_result=True
436
+ )
521
437
  return result
522
438
 
523
439
  def get_own_hardware_details(self):
524
- hardware_list_data = self.get_hardware_list(
440
+ hardware_list_result = self.get_hardware_list(
525
441
  fingerprint=self.primitive.host_config.get("fingerprint")
526
442
  )
527
- hardware = hardware_list_data.get("hardwareList").get("edges")[0].get("node")
443
+ hardware = (
444
+ hardware_list_result.data.get("hardwareList").get("edges")[0].get("node")
445
+ )
446
+ return hardware
447
+
448
+ def get_hardware_from_slug_or_id(self, hardware_identifier: str):
449
+ is_id = False
450
+ is_slug = False
451
+ # first check if the hardware_identifier is a slug or ID
452
+ try:
453
+ type_name, id = from_base64(hardware_identifier)
454
+
455
+ is_id = True
456
+ if type_name == "Hardware":
457
+ is_hardware_type = True
458
+ else:
459
+ raise Exception(
460
+ f"ID was not for Hardware, you supplied an ID for a {type_name}"
461
+ )
462
+
463
+ except ValueError:
464
+ is_slug = True
465
+
466
+ hardware = None
467
+
468
+ if is_id and is_hardware_type:
469
+ hardware_list_result = self.get_hardware_list(slug=hardware_identifier)
470
+ if edges := hardware_list_result.data["hardwareList"]["edges"]:
471
+ hardware = edges[0]["node"]
472
+ else:
473
+ raise Exception(f"No hardware found with slug {hardware_identifier}")
474
+ elif is_slug:
475
+ hardware_list_result = self.get_hardware_list(slug=hardware_identifier)
476
+ if edges := hardware_list_result.data["hardwareList"]["edges"]:
477
+ hardware = edges[0]["node"]
478
+ else:
479
+ raise Exception(f"No hardware found with slug {hardware_identifier}")
480
+
528
481
  return hardware
@@ -1,9 +1,9 @@
1
+ import typing
2
+
1
3
  import click
2
4
 
3
5
  from ..utils.printer import print_result
4
6
 
5
- import typing
6
-
7
7
  if typing.TYPE_CHECKING:
8
8
  from ..client import Primitive
9
9
 
@@ -31,7 +31,7 @@ def register_command(context):
31
31
  primitive: Primitive = context.obj.get("PRIMITIVE")
32
32
  result = primitive.hardware.register()
33
33
  color = "green" if result else "red"
34
- if result:
34
+ if result.data.get("registerHardware"):
35
35
  message = "Hardware registered successfully"
36
36
  else:
37
37
  message = (
@@ -45,9 +45,19 @@ def register_command(context):
45
45
  def checkin_command(context):
46
46
  """Checkin Hardware with Primitive"""
47
47
  primitive: Primitive = context.obj.get("PRIMITIVE")
48
- result = primitive.hardware.check_in_http()
49
- if messages := result.get("checkIn").get("messages"):
48
+ check_in_http_result = primitive.hardware.check_in_http()
49
+ if messages := check_in_http_result.data.get("checkIn").get("messages"):
50
50
  print_result(message=messages, context=context, fg="yellow")
51
51
  else:
52
52
  message = "Hardware checked in successfully"
53
53
  print_result(message=message, context=context, fg="green")
54
+
55
+
56
+ @cli.command("list")
57
+ @click.pass_context
58
+ def list_command(context):
59
+ """List Hardware"""
60
+ primitive: Primitive = context.obj.get("PRIMITIVE")
61
+ get_hardware_list_result = primitive.hardware.get_hardware_list()
62
+ message = get_hardware_list_result.data
63
+ print_result(message=message, context=context)
File without changes
@@ -0,0 +1,22 @@
1
+ hardware_fragment = """
2
+ fragment HardwareFragment on Hardware {
3
+ id
4
+ pk
5
+ name
6
+ slug
7
+ createdAt
8
+ updatedAt
9
+ isAvailable
10
+ isOnline
11
+ isQuarantined
12
+ isHealthy
13
+ capabilities {
14
+ id
15
+ pk
16
+ }
17
+ activeReservation {
18
+ id
19
+ pk
20
+ }
21
+ }
22
+ """
@@ -0,0 +1,45 @@
1
+ from primitive.graphql.utility_fragments import operation_info_fragment
2
+
3
+ register_hardware_mutation = (
4
+ operation_info_fragment
5
+ + """
6
+ mutation registerHardware($input: RegisterHardwareInput!) {
7
+ registerHardware(input: $input) {
8
+ ... on Hardware {
9
+ fingerprint
10
+ }
11
+ ...OperationInfoFragment
12
+ }
13
+ }
14
+ """
15
+ )
16
+
17
+ hardware_update_mutation = (
18
+ operation_info_fragment
19
+ + """
20
+ mutation hardwareUpdate($input: HardwareUpdateInput!) {
21
+ hardwareUpdate(input: $input) {
22
+ ... on Hardware {
23
+ systemInfo
24
+ }
25
+ ...OperationInfoFragment
26
+ }
27
+ }
28
+ """
29
+ )
30
+
31
+ hardware_checkin_mutation = (
32
+ operation_info_fragment
33
+ + """
34
+ mutation checkIn($input: CheckInInput!) {
35
+ checkIn(input: $input) {
36
+ ... on Hardware {
37
+ createdAt
38
+ updatedAt
39
+ lastCheckIn
40
+ }
41
+ ...OperationInfoFragment
42
+ }
43
+ }
44
+ """
45
+ )
@@ -0,0 +1,31 @@
1
+ from .fragments import hardware_fragment
2
+
3
+ hardware_list = (
4
+ hardware_fragment
5
+ + """
6
+
7
+ query hardwareList(
8
+ $before: String
9
+ $after: String
10
+ $first: Int
11
+ $last: Int
12
+ $filters: HardwareFilters
13
+ ) {
14
+ hardwareList(
15
+ before: $before
16
+ after: $after
17
+ first: $first
18
+ last: $last
19
+ filters: $filters
20
+ ) {
21
+ totalCount
22
+ edges {
23
+ cursor
24
+ node {
25
+ ...HardwareFragment
26
+ }
27
+ }
28
+ }
29
+ }
30
+ """
31
+ )
File without changes