Comparing changes
v0.5.0
→
v0.5.1
6 commits
22 files changed
Commits
Changed files (22)
.github
workflows
lib
scim
kit
spec
scim
kit
.github/workflows/ci.yml
@@ -0,0 +1,36 @@
+name: ci
+on: [push]
+jobs:
+ build:
+ runs-on: ubuntu-latest
+ strategy:
+ matrix:
+ ruby: [ '2.5', '2.6', '2.7' ]
+ name: RSpec Ruby ${{ matrix.ruby }}
+ steps:
+ - uses: actions/checkout@v2
+ with:
+ lfs: true
+ submodules: recursive
+ - uses: actions/setup-ruby@v1
+ with:
+ ruby-version: ${{ matrix.ruby }}
+ - name: setup
+ run: ./bin/setup
+ - name: test
+ run: ./bin/test
+ lint:
+ runs-on: ubuntu-latest
+ name: Lint
+ steps:
+ - uses: actions/checkout@v2
+ with:
+ lfs: true
+ submodules: recursive
+ - uses: actions/setup-ruby@v1
+ with:
+ ruby-version: 2.7
+ - name: setup
+ run: ./bin/setup
+ - name: lint
+ run: ./bin/lint
bin/cibuild
@@ -1,22 +1,21 @@
#!/bin/sh
-# script/cibuild: Setup environment for CI to run tests. This is primarily
-# designed to run on the continuous integration server.
-
set -e
-cd "$(dirname "$0")/.."
-
-echo ["$(date "+%H:%M:%S")"] "==> Started at…"
+[ -z "$DEBUG" ] || set -x
-# GC customizations
+cd "$(dirname "$0")/.."
export RUBY_GC_MALLOC_LIMIT=79000000
export RUBY_GC_HEAP_INIT_SLOTS=800000
export RUBY_HEAP_FREE_MIN=100000
export RUBY_HEAP_SLOTS_INCREMENT=400000
export RUBY_HEAP_SLOTS_GROWTH_FACTOR=1
-ruby -v
-gem install bundler --conservative
+echo ["$(date "+%H:%M:%S")"] "==> Running setup…"
+bin/setup
+
+echo ["$(date "+%H:%M:%S")"] "==> Running tests…"
bin/test
+
+echo ["$(date "+%H:%M:%S")"] "==> Running linters…"
bin/lint
bin/lint
@@ -2,10 +2,8 @@
set -e
-[ -z "$DEBUG" ] || set -x
+cd "$(dirname "$0")/.."
-echo [$(date "+%H:%M:%S")] "==> Running setup…"
-bin/setup
+export RUBYOPT='-W0'
-echo [$(date "+%H:%M:%S")] "==> Running linters…"
bundle exec rake lint
bin/setup
@@ -1,6 +1,7 @@
#!/usr/bin/env bash
set -euo pipefail
IFS=$'\n\t'
-set -vx
+ruby -v
+gem install bundler --conservative -v '~> 2.0'
bundle check || bundle install --jobs "$(sysctl -n hw.ncpu || nproc)"
bin/shipit
@@ -0,0 +1,8 @@
+#!/bin/sh
+
+set -e
+
+cd "$(dirname "$0")/.."
+
+bin/cibuild
+bundle exec rake release
bin/test
@@ -1,21 +1,9 @@
-#!/bin/bash
-
-# script/test: Run test suite for application. Optionally pass in a path to an
-# individual test file to run a single test.
-
+#!/bin/sh
set -e
cd "$(dirname "$0")/.."
-[ -z "$DEBUG" ] || set -x
-
-echo ["$(date "+%H:%M:%S")"] "==> Running setup…"
-bin/setup
+export RUBYOPT='-W0'
-echo ["$(date "+%H:%M:%S")"] "==> Running tests…"
-if [[ $# -eq 0 ]]; then
- bundle exec rake spec
-else
- bundle exec rspec "$1"
-fi
+bundle exec rspec "$@"
lib/scim/kit/v2/templates/attribute.json.jbuilder
@@ -3,7 +3,7 @@
json.key_format! camelize: :lower
if _type.complex? && !_type.multi_valued
json.set! _type.name do
- dynamic_attributes.values.each do |attribute|
+ dynamic_attributes.each_value do |attribute|
render attribute, json: json
end
end
lib/scim/kit/v2/attribute_type.rb
@@ -108,7 +108,7 @@ module Scim
def valid_complex?(item)
return false unless item.is_a?(Hash)
- item.keys.each do |key|
+ item.each_key do |key|
return false unless type_for(key)&.valid?(item[key])
end
end
lib/scim/kit/v2/configuration.rb
@@ -40,7 +40,8 @@ module Scim
attr_accessor :resource_types
attr_accessor :schemas
- def initialize
+ def initialize(http: Scim::Kit::Http.new)
+ @http = http
@resource_types = {}
@schemas = {}
@@ -48,9 +49,11 @@ module Scim
end
def load_from(base_url)
+ base_url = "#{base_url}/"
uri = URI.join(base_url, 'ServiceProviderConfig')
- self.service_provider_configuration =
- ServiceProviderConfiguration.parse(client.get(uri).body)
+ json = http.get(uri)
+
+ self.service_provider_configuration = ServiceProviderConfiguration.parse(json, json)
load_items(base_url, 'Schemas', Schema, schemas)
load_items(base_url, 'ResourceTypes', ResourceType, resource_types)
@@ -58,25 +61,15 @@ module Scim
private
+ attr_reader :http
+
def load_items(base_url, path, type, items)
- response = client.get(URI.join(base_url, path), headers: headers)
- hashes = JSON.parse(response.body, symbolize_names: true)
+ hashes = http.get(URI.join(base_url, path))
hashes.each do |hash|
item = type.from(hash)
items[item.id] = item
end
end
-
- def client
- @client ||= Net::Hippie::Client.new
- end
-
- def headers
- {
- 'Accept' => 'application/scim+json',
- 'Content-Type' => 'application/scim+json'
- }
- end
end
end
end
lib/scim/kit/http.rb
@@ -0,0 +1,47 @@
+# frozen_string_literal: true
+
+module Scim
+ module Kit
+ class Http
+ attr_reader :driver, :retries
+
+ def initialize(driver: Http.default_driver, retries: 3)
+ @driver = driver
+ @retries = retries
+ end
+
+ def get(uri)
+ driver.with_retry(retries: retries) do |client|
+ response = client.get(uri)
+ ok?(response) ? JSON.parse(response.body, symbolize_names: true) : {}
+ end
+ rescue *Net::Hippie::CONNECTION_ERRORS => error
+ Scim::Kit.logger.error(error)
+ {}
+ end
+
+ def self.default_driver
+ @default_driver ||= Net::Hippie::Client.new(headers: headers).tap do |http|
+ http.logger = Scim::Kit.logger
+ http.open_timeout = 1
+ http.read_timeout = 5
+ http.follow_redirects = 3
+ end
+ end
+
+ def self.headers
+ {
+ 'Accept' => 'application/scim+json',
+ 'Content-Type' => 'application/scim+json',
+ 'User-Agent' => "scim/kit #{Scim::Kit::VERSION}"
+ }
+ end
+
+ private
+
+ def ok?(response)
+ response.is_a?(Net::HTTPSuccess)
+ end
+ end
+ end
+end
lib/scim/kit/v2.rb
@@ -68,7 +68,7 @@ module Scim
false
end
},
- reference: ->(x) { x =~ /\A#{URI.regexp(%w[http https])}\z/ },
+ reference: ->(x) { x =~ /\A#{URI::DEFAULT_PARSER.make_regexp(%w[http https])}\z/ },
string: ->(x) { x.is_a?(String) }
}.freeze
lib/scim/kit/version.rb
@@ -2,6 +2,6 @@
module Scim
module Kit
- VERSION = '0.5.0'
+ VERSION = '0.5.1'
end
end
lib/scim/kit.rb
@@ -10,6 +10,7 @@ require 'tilt'
require 'tilt/jbuilder'
require 'scim/kit/dynamic_attributes'
+require 'scim/kit/http'
require 'scim/kit/templatable'
require 'scim/kit/template'
require 'scim/kit/v2'
spec/scim/kit/v2/filter_spec.rb
@@ -35,9 +35,9 @@ RSpec.describe Scim::Kit::V2::Filter do
specify { expect(subject.parse_with_debug('userName eq "jeramy@ziemann.biz"')).to be_truthy }
specify { expect(subject.parse_with_debug(%((title pr) and (userType eq "Employee")))).to be_truthy }
- specify { expect(subject.attribute_expression.parse_with_debug(%(title pr and userType eq "Employee"))).not_to be_truthy }
+ specify { expect(subject.attribute_expression).not_to parse(%(title pr and userType eq "Employee")) }
specify { expect(subject.logical_expression.parse_with_debug(%((title pr) and (userType eq "Employee")))).to be_truthy }
- specify { expect(subject.value_path.parse_with_debug(%(title pr and userType eq "Employee"))).not_to be_truthy }
+ specify { expect(subject.value_path).not_to parse(%(title pr and userType eq "Employee")) }
[
'emails[(type eq "work") and (value co "@example.com")]'
spec/scim/kit/v2/resource_spec.rb
@@ -49,7 +49,7 @@ RSpec.describe Scim::Kit::V2::Resource do
end
end
- context 'with attribute named "type"' do
+ context 'with attribute named "members"' do
before do
schema.add_attribute(name: 'members') do |attribute|
attribute.mutability = :read_only
.rspec
@@ -1,3 +1,3 @@
---format documentation
+--format progress
--color
--require spec_helper
.rubocop.yml
@@ -9,19 +9,49 @@ AllCops:
- 'vendor/**/*'
TargetRubyVersion: 2.5
+Layout/ArgumentAlignment:
+ EnforcedStyle: with_fixed_indentation
+
+Layout/EndOfLine:
+ EnforcedStyle: lf
+
Layout/FirstArrayElementIndentation:
EnforcedStyle: consistent
+Layout/LineLength:
+ Exclude:
+ - 'spec/**/*.rb'
+ IgnoredPatterns:
+ - '^#*'
+
+Layout/MultilineMethodCallIndentation:
+ Enabled: true
+ EnforcedStyle: indented
+
+Layout/ParameterAlignment:
+ Enabled: true
+ EnforcedStyle: with_fixed_indentation
+ IndentationWidth: 2
+
+Lint/AmbiguousBlockAssociation:
+ Exclude:
+ - 'spec/**/*.rb'
+
+Lint/RaiseException:
+ Enabled: true
+
+Lint/StructNewOverride:
+ Enabled: true
+
Metrics/BlockLength:
Exclude:
- '*.gemspec'
+ - 'Rakefile'
- 'spec/**/*.rb'
-Metrics/LineLength:
+Metrics/ModuleLength:
Exclude:
- 'spec/**/*.rb'
- IgnoredPatterns:
- - '^#*'
Naming/FileName:
Exclude:
@@ -30,6 +60,30 @@ Naming/FileName:
Naming/RescuedExceptionsVariableName:
PreferredName: error
+Style/Documentation:
+ Enabled: false
+
+Style/HashEachMethods:
+ Enabled: true
+
+Style/HashTransformKeys:
+ Enabled: true
+
+Style/HashTransformValues:
+ Enabled: true
+
+Style/StringLiterals:
+ EnforcedStyle: 'single_quotes'
+
+Style/TrailingCommaInArrayLiteral:
+ Enabled: false
+
+Style/TrailingCommaInHashLiteral:
+ Enabled: false
+
+RSpec/FilePath:
+ Enabled: false
+
RSpec/NamedSubject:
Enabled: false
.travis.yml
@@ -1,9 +0,0 @@
----
-sudo: false
-language: ruby
-cache: bundler
-rvm:
- - 2.5.7
- - 2.6.5
- - 2.7.0
-before_install: gem install bundler -v 1.17.1
CHANGELOG.md
@@ -1,4 +1,4 @@
-Version 0.5.0
+Version 0.5.1
# Changelog
All notable changes to this project will be documented in this file.
@@ -7,7 +7,16 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
## [Unreleased]
-- nil
+
+## [0.5.1] - 2020-05-20
+### Fixed
+- Specify `Accept: application/scim+json` header when discovering a SCIM API.
+- Specify `Content-Type: application/scim+json` header when discovering a SCIM API.
+- Specify `User-Agent: scim/kit <version>` header when discovering a SCIM API.
+- Follow HTTP redirects when discovering a SCIM API.
+- Retry 3 times with backoff + jitter when a connection to a SCIM discovery API fails.
+- Specify a 1 second open timeout.
+- Specify a 5 second read timeout.
## [0.5.0] - 2020-01-21
### Added
@@ -44,8 +53,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- \_assign does not coerce values by default.
- errors are merged together instead of overwritten during attribute validation.
-[Unreleased]: https://github.com/mokhan/scim-kit/compare/v0.5.0...HEAD
-[0.4.0]: https://github.com/mokhan/scim-kit/compare/v0.4.0...v0.5.0
+[Unreleased]: https://github.com/mokhan/scim-kit/compare/v0.5.1...HEAD
+[0.5.1]: https://github.com/mokhan/scim-kit/compare/v0.5.0...v0.5.1
+[0.5.0]: https://github.com/mokhan/scim-kit/compare/v0.4.0...v0.5.0
[0.4.0]: https://github.com/mokhan/scim-kit/compare/v0.3.2...v0.4.0
[0.3.2]: https://github.com/mokhan/scim-kit/compare/v0.3.1...v0.3.2
[0.3.1]: https://github.com/mokhan/scim-kit/compare/v0.3.0...v0.3.1
Gemfile.lock
@@ -1,9 +1,9 @@
PATH
remote: .
specs:
- scim-kit (0.5.0)
+ scim-kit (0.5.1)
activemodel (>= 5.2.0)
- net-hippie (~> 0.2)
+ net-hippie (~> 0.3)
parslet (~> 1.8)
tilt (~> 2.0)
tilt-jbuilder (~> 0.7)
@@ -11,62 +11,62 @@ PATH
GEM
remote: https://rubygems.org/
specs:
- activemodel (6.0.2.1)
- activesupport (= 6.0.2.1)
- activesupport (6.0.2.1)
+ activemodel (6.0.3.1)
+ activesupport (= 6.0.3.1)
+ activesupport (6.0.3.1)
concurrent-ruby (~> 1.0, >= 1.0.2)
i18n (>= 0.7, < 2)
minitest (~> 5.1)
tzinfo (~> 1.1)
- zeitwerk (~> 2.2)
+ zeitwerk (~> 2.2, >= 2.2.2)
addressable (2.7.0)
public_suffix (>= 2.0.2, < 5.0)
ast (2.4.0)
bundler-audit (0.6.1)
bundler (>= 1.2.0, < 3)
thor (~> 0.18)
- byebug (11.1.0)
- concurrent-ruby (1.1.5)
+ byebug (11.1.3)
+ concurrent-ruby (1.1.6)
crack (0.4.3)
safe_yaml (~> 1.0.0)
diff-lcs (1.3)
- ffaker (2.13.0)
- hashdiff (1.0.0)
+ ffaker (2.14.0)
+ hashdiff (1.0.1)
i18n (1.8.2)
concurrent-ruby (~> 1.0)
- jaro_winkler (1.5.4)
- jbuilder (2.9.1)
- activesupport (>= 4.2.0)
- minitest (5.14.0)
- net-hippie (0.3.1)
+ jbuilder (2.10.0)
+ activesupport (>= 5.0.0)
+ minitest (5.14.1)
+ net-hippie (0.3.2)
parallel (1.19.1)
- parser (2.7.0.2)
+ parser (2.7.1.2)
ast (~> 2.4.0)
parslet (1.8.2)
- public_suffix (4.0.3)
+ public_suffix (4.0.5)
rainbow (3.0.0)
rake (13.0.1)
+ rexml (3.2.4)
rspec (3.9.0)
rspec-core (~> 3.9.0)
rspec-expectations (~> 3.9.0)
rspec-mocks (~> 3.9.0)
- rspec-core (3.9.1)
- rspec-support (~> 3.9.1)
- rspec-expectations (3.9.0)
+ rspec-core (3.9.2)
+ rspec-support (~> 3.9.3)
+ rspec-expectations (3.9.2)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.9.0)
rspec-mocks (3.9.1)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.9.0)
- rspec-support (3.9.2)
- rubocop (0.79.0)
- jaro_winkler (~> 1.5.1)
+ rspec-support (3.9.3)
+ rubocop (0.83.0)
parallel (~> 1.10)
parser (>= 2.7.0.1)
rainbow (>= 2.2.2, < 4.0)
+ rexml
ruby-progressbar (~> 1.7)
- unicode-display_width (>= 1.4.0, < 1.7)
- rubocop-rspec (1.37.1)
+ unicode-display_width (>= 1.4.0, < 2.0)
+ rubocop-rspec (1.39.0)
rubocop (>= 0.68.1)
ruby-progressbar (1.10.1)
safe_yaml (1.0.5)
@@ -76,20 +76,20 @@ GEM
tilt-jbuilder (0.7.1)
jbuilder
tilt (>= 1.3.0, < 3)
- tzinfo (1.2.6)
+ tzinfo (1.2.7)
thread_safe (~> 0.1)
- unicode-display_width (1.6.1)
- webmock (3.8.0)
+ unicode-display_width (1.7.0)
+ webmock (3.8.3)
addressable (>= 2.3.6)
crack (>= 0.3.2)
hashdiff (>= 0.4.0, < 2.0.0)
- zeitwerk (2.2.2)
+ zeitwerk (2.3.0)
PLATFORMS
ruby
DEPENDENCIES
- bundler (~> 1.17)
+ bundler (~> 2.0)
bundler-audit (~> 0.6)
byebug
ffaker (~> 2.7)
@@ -101,4 +101,4 @@ DEPENDENCIES
webmock (~> 3.5)
BUNDLED WITH
- 1.17.3
+ 2.1.4
README.md
@@ -1,6 +1,6 @@
# Scim::Kit
-[](https://travis-ci.org/mokhan/scim-kit)
+[](https://github.com/mokhan/scim-kit/actions)
[](https://codeclimate.com/github/mokhan/scim-kit)
[](https://rubygems.org/gems/scim-kit)
scim-kit.gemspec
@@ -27,15 +27,15 @@ Gem::Specification.new do |spec|
File.basename(file)
end
spec.require_paths = ['lib']
- spec.required_ruby_version = '>= 2.5.0'
+ spec.required_ruby_version = Gem::Requirement.new('>= 2.5.0')
spec.metadata['yard.run'] = 'yri'
spec.add_dependency 'activemodel', '>= 5.2.0'
- spec.add_dependency 'net-hippie', '~> 0.2'
+ spec.add_dependency 'net-hippie', '~> 0.3'
spec.add_dependency 'parslet', '~> 1.8'
spec.add_dependency 'tilt', '~> 2.0'
spec.add_dependency 'tilt-jbuilder', '~> 0.7'
- spec.add_development_dependency 'bundler', '~> 1.17'
+ spec.add_development_dependency 'bundler', '~> 2.0'
spec.add_development_dependency 'bundler-audit', '~> 0.6'
spec.add_development_dependency 'byebug'
spec.add_development_dependency 'ffaker', '~> 2.7'