karafka-core 2.5.0 → 2.5.2

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 47aa33db15ba75b9696851ac4f999a52392394336fe12661a1d66158169619ec
4
- data.tar.gz: 5ad3131cfe276d534f5a2b3042eb0fb4f09c214a92671ab6f6b9275b060b9fc5
3
+ metadata.gz: dcd7aa040c5e5025430de4755c6e3de2850f8e697a8222328a304f571d9bd1fc
4
+ data.tar.gz: b3498c28bf38256e7012a950a51f464d66a503c045227f1dde0e503b6d9550c3
5
5
  SHA512:
6
- metadata.gz: e82ac91941d6a048c668f78269c2574a44986d4eb0123ba64384027e2ef79c41e5e4f15e7e9402a9e9bc67917f23803af5d7be704e0105e8835df6d326d953c5
7
- data.tar.gz: 94b3680f843a482afdc7b9cec4977e8eeb42e87799d6a78aa86830942e16d07cdcb2b9f5fd00e419a0ecb4d0145ef17e2c63c0aad9e13d4b1fbc639dab91cc75
6
+ metadata.gz: 350399becfcf8a702a9c106cb6f6310dc57255549fbe54cd7bbadae4e1c2c1e13efc53b9d60972c20c2a057775483461f73f60dc2839da964db39de47b7f608d
7
+ data.tar.gz: 4b94de1f08121280d3321dad105487e7b3e3ddaefe2ba2d4a3dd67a5c2fe3b23cb5588fa707d8ad513346c860749f9389431751b26c1688b19104a585bda4de6
@@ -1,4 +1,4 @@
1
- name: ci
1
+ name: CI
2
2
 
3
3
  concurrency:
4
4
  group: ${{ github.workflow }}-${{ github.ref }}
@@ -40,7 +40,7 @@ jobs:
40
40
  run: "[ -e $APT_DEPS ] || sudo apt-get install -y --no-install-recommends $APT_DEPS"
41
41
 
42
42
  - name: Set up Ruby
43
- uses: ruby/setup-ruby@e34163cd15f4bb403dcd72d98e295997e6a55798 # v1.238.0
43
+ uses: ruby/setup-ruby@13e7a03dc3ac6c3798f4570bfead2aed4d96abfb # v1.244.0
44
44
  with:
45
45
  ruby-version: ${{matrix.ruby}}
46
46
  bundler: 'latest'
@@ -71,7 +71,7 @@ jobs:
71
71
  with:
72
72
  fetch-depth: 0
73
73
  - name: Set up Ruby
74
- uses: ruby/setup-ruby@e34163cd15f4bb403dcd72d98e295997e6a55798 # v1.238.0
74
+ uses: ruby/setup-ruby@13e7a03dc3ac6c3798f4570bfead2aed4d96abfb # v1.244.0
75
75
  with:
76
76
  ruby-version: 3.4
77
77
  - name: Install latest bundler
@@ -0,0 +1,35 @@
1
+ name: Push Gem
2
+
3
+ on:
4
+ push:
5
+ tags:
6
+ - v*
7
+
8
+ permissions:
9
+ contents: read
10
+
11
+ jobs:
12
+ push:
13
+ if: github.repository_owner == 'karafka'
14
+ runs-on: ubuntu-latest
15
+ environment: deployment
16
+
17
+ permissions:
18
+ contents: write
19
+ id-token: write
20
+
21
+ steps:
22
+ - uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
23
+ with:
24
+ fetch-depth: 0
25
+
26
+ - name: Set up Ruby
27
+ uses: ruby/setup-ruby@13e7a03dc3ac6c3798f4570bfead2aed4d96abfb # v1.244.0
28
+ with:
29
+ bundler-cache: false
30
+
31
+ - name: Bundle install
32
+ run: |
33
+ bundle install --jobs 4 --retry 3
34
+
35
+ - uses: rubygems/release-gem@a25424ba2ba8b387abc8ef40807c2c85b96cbe32 # v1.1.1
data/CHANGELOG.md CHANGED
@@ -1,5 +1,14 @@
1
1
  # Karafka Core Changelog
2
2
 
3
+ ## 2.5.2 (2025-06-11)
4
+ - [Enhancement] Support `#unsubscribe`.
5
+ - [Enhancement] Allow for providing a root scope path for error keys.
6
+ - [Fix] Fix a bug where on no errors the result would be an array instead of a hash.
7
+ - [Fix] Fix spec hanging when Kafka cluster on 9092 is running.
8
+
9
+ ## 2.5.1 (2025-05-23)
10
+ - [Change] Move to trusted-publishers and remove signing since no longer needed.
11
+
3
12
  ## 2.5.0 (2025-05-21)
4
13
  - [Change] Set minimum `karafka-rdkafka` on `0.19.2` to support new features.
5
14
 
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- karafka-core (2.5.0)
4
+ karafka-core (2.5.2)
5
5
  karafka-rdkafka (>= 0.19.2, < 0.21.0)
6
6
  logger (>= 1.6.0)
7
7
 
@@ -22,26 +22,26 @@ GEM
22
22
  ffi (1.17.2-x86_64-darwin)
23
23
  ffi (1.17.2-x86_64-linux-gnu)
24
24
  ffi (1.17.2-x86_64-linux-musl)
25
- karafka-rdkafka (0.19.2)
25
+ karafka-rdkafka (0.19.5)
26
26
  ffi (~> 1.15)
27
27
  mini_portile2 (~> 2.6)
28
28
  rake (> 12)
29
29
  logger (1.7.0)
30
30
  mini_portile2 (2.8.9)
31
- rake (13.2.1)
32
- rspec (3.13.0)
31
+ rake (13.3.0)
32
+ rspec (3.13.1)
33
33
  rspec-core (~> 3.13.0)
34
34
  rspec-expectations (~> 3.13.0)
35
35
  rspec-mocks (~> 3.13.0)
36
- rspec-core (3.13.3)
36
+ rspec-core (3.13.4)
37
37
  rspec-support (~> 3.13.0)
38
- rspec-expectations (3.13.4)
38
+ rspec-expectations (3.13.5)
39
39
  diff-lcs (>= 1.2.0, < 2.0)
40
40
  rspec-support (~> 3.13.0)
41
- rspec-mocks (3.13.4)
41
+ rspec-mocks (3.13.5)
42
42
  diff-lcs (>= 1.2.0, < 2.0)
43
43
  rspec-support (~> 3.13.0)
44
- rspec-support (3.13.3)
44
+ rspec-support (3.13.4)
45
45
  simplecov (0.22.0)
46
46
  docile (~> 1.1)
47
47
  simplecov-html (~> 0.11)
data/Rakefile ADDED
@@ -0,0 +1,4 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'bundler/setup'
4
+ require 'bundler/gem_tasks'
data/karafka-core.gemspec CHANGED
@@ -21,11 +21,6 @@ Gem::Specification.new do |spec|
21
21
 
22
22
  spec.required_ruby_version = '>= 3.1.0'
23
23
 
24
- if $PROGRAM_NAME.end_with?('gem')
25
- spec.signing_key = File.expand_path('~/.ssh/gem-private_key.pem')
26
- end
27
-
28
- spec.cert_chain = %w[certs/cert.pem]
29
24
  spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(spec)/}) }
30
25
  spec.require_paths = %w[lib]
31
26
 
@@ -78,18 +78,20 @@ module Karafka
78
78
  # Runs the validation
79
79
  #
80
80
  # @param data [Hash] hash with data we want to validate
81
+ # @param scope [Array<String>] scope of this contract (if any) or empty array if no parent
82
+ # scope is needed if contract starts from root
81
83
  # @return [Result] validaton result
82
- def call(data)
84
+ def call(data, scope: [])
83
85
  errors = []
84
86
 
85
87
  self.class.rules.each do |rule|
86
88
  case rule.type
87
89
  when :required
88
- validate_required(data, rule, errors)
90
+ validate_required(data, rule, errors, scope)
89
91
  when :optional
90
- validate_optional(data, rule, errors)
92
+ validate_optional(data, rule, errors, scope)
91
93
  when :virtual
92
- validate_virtual(data, rule, errors)
94
+ validate_virtual(data, rule, errors, scope)
93
95
  end
94
96
  end
95
97
 
@@ -98,11 +100,13 @@ module Karafka
98
100
 
99
101
  # @param data [Hash] data for validation
100
102
  # @param error_class [Class] error class that should be used when validation fails
103
+ # @param scope [Array<String>] scope of this contract (if any) or empty array if no parent
104
+ # scope is needed if contract starts from root
101
105
  # @return [Boolean] true
102
106
  # @raise [StandardError] any error provided in the error_class that inherits from the
103
107
  # standard error
104
- def validate!(data, error_class)
105
- result = call(data)
108
+ def validate!(data, error_class, scope: [])
109
+ result = call(data, scope: scope)
106
110
 
107
111
  return true if result.success?
108
112
 
@@ -117,19 +121,20 @@ module Karafka
117
121
  # @param data [Hash] input hash
118
122
  # @param rule [Rule] validation rule
119
123
  # @param errors [Array] array with errors from previous rules (if any)
120
- def validate_required(data, rule, errors)
124
+ # @param scope [Array<String>]
125
+ def validate_required(data, rule, errors, scope)
121
126
  for_checking = dig(data, rule.path)
122
127
 
123
128
  # We need to compare `DIG_MISS` against stuff because of the ownership of the `#==`
124
129
  # method
125
130
  if DIG_MISS == for_checking
126
- errors << [rule.path, :missing]
131
+ errors << [scope + rule.path, :missing]
127
132
  else
128
133
  result = rule.validator.call(for_checking, data, errors, self)
129
134
 
130
135
  return if result == true
131
136
 
132
- errors << [rule.path, result || :format]
137
+ errors << [scope + rule.path, result || :format]
133
138
  end
134
139
  end
135
140
 
@@ -139,7 +144,8 @@ module Karafka
139
144
  # @param data [Hash] input hash
140
145
  # @param rule [Rule] validation rule
141
146
  # @param errors [Array] array with errors from previous rules (if any)
142
- def validate_optional(data, rule, errors)
147
+ # @param scope [Array<String>]
148
+ def validate_optional(data, rule, errors, scope)
143
149
  for_checking = dig(data, rule.path)
144
150
 
145
151
  return if DIG_MISS == for_checking
@@ -148,7 +154,7 @@ module Karafka
148
154
 
149
155
  return if result == true
150
156
 
151
- errors << [rule.path, result || :format]
157
+ errors << [scope + rule.path, result || :format]
152
158
  end
153
159
 
154
160
  # Runs validation for rules on virtual fields (aggregates, etc) and adds errors (if any) to
@@ -157,11 +163,18 @@ module Karafka
157
163
  # @param data [Hash] input hash
158
164
  # @param rule [Rule] validation rule
159
165
  # @param errors [Array] array with errors from previous rules (if any)
160
- def validate_virtual(data, rule, errors)
166
+ # @param scope [Array<String>]
167
+ def validate_virtual(data, rule, errors, scope)
161
168
  result = rule.validator.call(data, errors, self)
162
169
 
163
170
  return if result == true
164
171
 
172
+ if result
173
+ result.each do |sub_result|
174
+ sub_result[0] = scope + sub_result[0]
175
+ end
176
+ end
177
+
165
178
  errors.push(*result)
166
179
  end
167
180
 
@@ -14,7 +14,7 @@ module Karafka
14
14
  def initialize(errors, contract)
15
15
  # Short track to skip object allocation for the happy path
16
16
  if errors.empty?
17
- @errors = errors
17
+ @errors = {}
18
18
  return
19
19
  end
20
20
 
@@ -41,7 +41,8 @@ module Karafka
41
41
 
42
42
  private
43
43
 
44
- # Builds message based on the error messages
44
+ # Builds message based on the error messages and scope
45
+ #
45
46
  # @param contract [Object] contract for which we build the result
46
47
  # @param scope [Symbol] path to the key that has an error
47
48
  # @param error_key [Symbol] error key for yaml errors lookup
@@ -49,6 +50,25 @@ module Karafka
49
50
  def build_message(contract, scope, error_key)
50
51
  messages = contract.class.config.error_messages
51
52
 
53
+ # Split scope into parts for progressive checking
54
+ scope_parts = scope.to_s.split('.')
55
+
56
+ # Try full scope first, then progressively remove from beginning
57
+ # This allows us to have full path scoped errors but can also be used as a fallback,
58
+ # when scopes are dynamic. For example 'consumer_group_name.topic_name.name_format'
59
+ (0..scope_parts.length).each do |i|
60
+ current_scope_parts = scope_parts[i..]
61
+
62
+ key = if current_scope_parts.empty?
63
+ error_key.to_s
64
+ else
65
+ "#{current_scope_parts.join('.')}_#{error_key}"
66
+ end
67
+
68
+ return messages[key] if messages.key?(key)
69
+ end
70
+
71
+ # If nothing found, raise the original error
52
72
  messages.fetch(error_key.to_s) do
53
73
  messages.fetch("#{scope}_#{error_key}")
54
74
  end
@@ -42,6 +42,14 @@ module Karafka
42
42
  @notifications_bus.subscribe(*args, &block)
43
43
  end
44
44
 
45
+ # Allows for removal of whatever was subscribed
46
+ #
47
+ # @param listener_or_block [Object] object that is subscribed whether this is a listener
48
+ # instance or a block.
49
+ def unsubscribe(listener_or_block)
50
+ @notifications_bus.unsubscribe(listener_or_block)
51
+ end
52
+
45
53
  # @return [Hash<String, Array>] hash where keys are events and values are arrays with
46
54
  # listeners subscribed to particular events. Since different events may have different
47
55
  # listeners, this is returned that way.
@@ -89,6 +89,21 @@ module Karafka
89
89
  end
90
90
  end
91
91
 
92
+ # Allows for unsubscription from events
93
+ # This method will remove the listener/block from all events where it's currently subscribed.
94
+ #
95
+ # @param listener_or_block [Object] listener object or block to remove from all events
96
+ #
97
+ # @example Unsubscribe using listener (removes from all events where it's subscribed)
98
+ # unsubscribe(my_listener)
99
+ def unsubscribe(listener_or_block)
100
+ @mutex.synchronize do
101
+ @listeners.each_value do |event_listeners|
102
+ event_listeners.delete(listener_or_block)
103
+ end
104
+ end
105
+ end
106
+
92
107
  # Allows for code instrumentation
93
108
  # Runs the provided code and sends the instrumentation details to all registered listeners
94
109
  #
@@ -4,6 +4,6 @@ module Karafka
4
4
  module Core
5
5
  # Current Karafka::Core version
6
6
  # We follow the versioning schema of given Karafka version
7
- VERSION = '2.5.0'
7
+ VERSION = '2.5.2'
8
8
  end
9
9
  end
metadata CHANGED
@@ -1,39 +1,12 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: karafka-core
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.5.0
4
+ version: 2.5.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Maciej Mensfeld
8
8
  bindir: bin
9
- cert_chain:
10
- - |
11
- -----BEGIN CERTIFICATE-----
12
- MIIEcDCCAtigAwIBAgIBATANBgkqhkiG9w0BAQsFADA/MRAwDgYDVQQDDAdjb250
13
- YWN0MRcwFQYKCZImiZPyLGQBGRYHa2FyYWZrYTESMBAGCgmSJomT8ixkARkWAmlv
14
- MB4XDTI0MDgyMzEwMTkyMFoXDTQ5MDgxNzEwMTkyMFowPzEQMA4GA1UEAwwHY29u
15
- dGFjdDEXMBUGCgmSJomT8ixkARkWB2thcmFma2ExEjAQBgoJkiaJk/IsZAEZFgJp
16
- bzCCAaIwDQYJKoZIhvcNAQEBBQADggGPADCCAYoCggGBAKjLhLjQqUlNayxkXnO+
17
- PsmCDs/KFIzhrsYMfLZRZNaWmzV3ujljMOdDjd4snM2X06C41iVdQPWjpe3j8vVe
18
- ZXEWR/twSbOP6Eeg8WVH2wCOo0x5i7yhVn4UBLH4JpfEMCbemVcWQ9ry9OMg4WpH
19
- Uu4dRwxFV7hzCz3p0QfNLRI4miAxnGWcnlD98IJRjBAksTuR1Llj0vbOrDGsL9ZT
20
- JeXP2gdRLd8SqzAFJEWrbeTBCBU7gfSh3oMg5SVDLjaqf7Kz5wC/8bDZydzanOxB
21
- T6CDXPsCnllmvTNx2ei2T5rGYJOzJeNTmJLLK6hJWUlAvaQSvCwZRvFJ0tVGLEoS
22
- flqSr6uGyyl1eMUsNmsH4BqPEYcAV6P2PKTv2vUR8AP0raDvZ3xL1TKvfRb8xRpo
23
- vPopCGlY5XBWEc6QERHfVLTIVsjnls2/Ujj4h8/TSfqqYnaHKefIMLbuD/tquMjD
24
- iWQsW2qStBV0T+U7FijKxVfrfqZP7GxQmDAc9o1iiyAa3QIDAQABo3cwdTAJBgNV
25
- HRMEAjAAMAsGA1UdDwQEAwIEsDAdBgNVHQ4EFgQU3O4dTXmvE7YpAkszGzR9DdL9
26
- sbEwHQYDVR0RBBYwFIESY29udGFjdEBrYXJhZmthLmlvMB0GA1UdEgQWMBSBEmNv
27
- bnRhY3RAa2FyYWZrYS5pbzANBgkqhkiG9w0BAQsFAAOCAYEAVKTfoLXn7mqdSxIR
28
- eqxcR6Huudg1jes81s1+X0uiRTR3hxxKZ3Y82cPsee9zYWyBrN8TA4KA0WILTru7
29
- Ygxvzha0SRPsSiaKLmgOJ+61ebI4+bOORzIJLpD6GxCxu1r7MI4+0r1u1xe0EWi8
30
- agkVo1k4Vi8cKMLm6Gl9b3wG9zQBw6fcgKwmpjKiNnOLP+OytzUANrIUJjoq6oal
31
- TC+f/Uc0TLaRqUaW/bejxzDWWHoM3SU6aoLPuerglzp9zZVzihXwx3jPLUVKDFpF
32
- Rl2lcBDxlpYGueGo0/oNzGJAAy6js8jhtHC9+19PD53vk7wHtFTZ/0ugDQYnwQ+x
33
- oml2fAAuVWpTBCgOVFe6XCQpMKopzoxQ1PjKztW2KYxgJdIBX87SnL3aWuBQmhRd
34
- i9zWxov0mr44TWegTVeypcWGd/0nxu1+QHVNHJrpqlPBRvwQsUm7fwmRInGpcaB8
35
- ap8wNYvryYzrzvzUxIVFBVM5PacgkFqRmolCa8I7tdKQN+R1
36
- -----END CERTIFICATE-----
9
+ cert_chain: []
37
10
  date: 1980-01-02 00:00:00.000000000 Z
38
11
  dependencies:
39
12
  - !ruby/object:Gem::Dependency
@@ -85,6 +58,7 @@ files:
85
58
  - ".github/ISSUE_TEMPLATE/bug_report.md"
86
59
  - ".github/ISSUE_TEMPLATE/feature_request.md"
87
60
  - ".github/workflows/ci.yml"
61
+ - ".github/workflows/push.yml"
88
62
  - ".github/workflows/verify-action-pins.yml"
89
63
  - ".gitignore"
90
64
  - ".rspec"
@@ -96,7 +70,7 @@ files:
96
70
  - Gemfile.lock
97
71
  - MIT-LICENSE
98
72
  - README.md
99
- - certs/cert.pem
73
+ - Rakefile
100
74
  - config/locales/errors.yml
101
75
  - karafka-core.gemspec
102
76
  - lib/karafka-core.rb
@@ -148,7 +122,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
148
122
  - !ruby/object:Gem::Version
149
123
  version: '0'
150
124
  requirements: []
151
- rubygems_version: 3.6.9
125
+ rubygems_version: 3.6.7
152
126
  specification_version: 4
153
127
  summary: Karafka ecosystem core modules
154
128
  test_files: []
checksums.yaml.gz.sig DELETED
Binary file
data/certs/cert.pem DELETED
@@ -1,26 +0,0 @@
1
- -----BEGIN CERTIFICATE-----
2
- MIIEcDCCAtigAwIBAgIBATANBgkqhkiG9w0BAQsFADA/MRAwDgYDVQQDDAdjb250
3
- YWN0MRcwFQYKCZImiZPyLGQBGRYHa2FyYWZrYTESMBAGCgmSJomT8ixkARkWAmlv
4
- MB4XDTI0MDgyMzEwMTkyMFoXDTQ5MDgxNzEwMTkyMFowPzEQMA4GA1UEAwwHY29u
5
- dGFjdDEXMBUGCgmSJomT8ixkARkWB2thcmFma2ExEjAQBgoJkiaJk/IsZAEZFgJp
6
- bzCCAaIwDQYJKoZIhvcNAQEBBQADggGPADCCAYoCggGBAKjLhLjQqUlNayxkXnO+
7
- PsmCDs/KFIzhrsYMfLZRZNaWmzV3ujljMOdDjd4snM2X06C41iVdQPWjpe3j8vVe
8
- ZXEWR/twSbOP6Eeg8WVH2wCOo0x5i7yhVn4UBLH4JpfEMCbemVcWQ9ry9OMg4WpH
9
- Uu4dRwxFV7hzCz3p0QfNLRI4miAxnGWcnlD98IJRjBAksTuR1Llj0vbOrDGsL9ZT
10
- JeXP2gdRLd8SqzAFJEWrbeTBCBU7gfSh3oMg5SVDLjaqf7Kz5wC/8bDZydzanOxB
11
- T6CDXPsCnllmvTNx2ei2T5rGYJOzJeNTmJLLK6hJWUlAvaQSvCwZRvFJ0tVGLEoS
12
- flqSr6uGyyl1eMUsNmsH4BqPEYcAV6P2PKTv2vUR8AP0raDvZ3xL1TKvfRb8xRpo
13
- vPopCGlY5XBWEc6QERHfVLTIVsjnls2/Ujj4h8/TSfqqYnaHKefIMLbuD/tquMjD
14
- iWQsW2qStBV0T+U7FijKxVfrfqZP7GxQmDAc9o1iiyAa3QIDAQABo3cwdTAJBgNV
15
- HRMEAjAAMAsGA1UdDwQEAwIEsDAdBgNVHQ4EFgQU3O4dTXmvE7YpAkszGzR9DdL9
16
- sbEwHQYDVR0RBBYwFIESY29udGFjdEBrYXJhZmthLmlvMB0GA1UdEgQWMBSBEmNv
17
- bnRhY3RAa2FyYWZrYS5pbzANBgkqhkiG9w0BAQsFAAOCAYEAVKTfoLXn7mqdSxIR
18
- eqxcR6Huudg1jes81s1+X0uiRTR3hxxKZ3Y82cPsee9zYWyBrN8TA4KA0WILTru7
19
- Ygxvzha0SRPsSiaKLmgOJ+61ebI4+bOORzIJLpD6GxCxu1r7MI4+0r1u1xe0EWi8
20
- agkVo1k4Vi8cKMLm6Gl9b3wG9zQBw6fcgKwmpjKiNnOLP+OytzUANrIUJjoq6oal
21
- TC+f/Uc0TLaRqUaW/bejxzDWWHoM3SU6aoLPuerglzp9zZVzihXwx3jPLUVKDFpF
22
- Rl2lcBDxlpYGueGo0/oNzGJAAy6js8jhtHC9+19PD53vk7wHtFTZ/0ugDQYnwQ+x
23
- oml2fAAuVWpTBCgOVFe6XCQpMKopzoxQ1PjKztW2KYxgJdIBX87SnL3aWuBQmhRd
24
- i9zWxov0mr44TWegTVeypcWGd/0nxu1+QHVNHJrpqlPBRvwQsUm7fwmRInGpcaB8
25
- ap8wNYvryYzrzvzUxIVFBVM5PacgkFqRmolCa8I7tdKQN+R1
26
- -----END CERTIFICATE-----
data.tar.gz.sig DELETED
Binary file
metadata.gz.sig DELETED
@@ -1,2 +0,0 @@
1
- ��h���^�UDM�$K6�M^i!��c�(Y�/����/� e?=����Iohr�e�.���M���]T9�p�un�*.6��7j�A,o]i�0n.c�/��oe���Lq�6��<�+^�.(~>?��������_Du����m�%{K�}�b���QҊ[
2
- I�q���"�ۦ�� �I3�����۳�ɣ��M�!U�Hχ�� �g��&�n_�|�}�E�,��~W3���N��r9/&K�5 E��g�R