Refactoring: Automatic RSpec VCR cassette name helper

This commit was prepared to support upcoming additions to the test suite
(specifically, better coverage for existing Twitter functionality).

These upcoming changes will depend heavily on VCR.[0]
(VCR is a Ruby gem that makes it easier to write and run tests
that call out to external services over HTTP
by "recording" HTTP transactions to a YAML file
and "replaying" them later.)

VCR is widely-used (4600 GitHub stars), but its API is a little clumsy--
You have to manually specify the name of a "cassette" file every time:

    it 'does something' do
      VCR.use_cassette('path/to/cassette') do
        ...
      end
    end

This commit adds an RSpec metadata config option
as a shorthand for the syntax above:

    it 'does something', :use_vcr do
      ...
    end

This config option automatically generates a cassette filename
based on the description of the example it's applied to.

=== Analysis of alternative approaches

Ideally, these auto-generated cassette filenames should be unique:
if filenames collide, multiple examples will share the same cassette.

A first attempt generated names based on `example.full_description`,
but that led to errors:

    Errno::ENAMETOOLONG:
      File name too long @ rb_sysopen - /opt/zammad/test/data/vcr_cassettes/models/ticket/article/ticket_article_callbacks_observers_async_transactions_-_auto-setting_of_outgoing_twitter_article_attributes_via_bg_jobs_when_the_original_channel_specified_in_ticket_preferences_was_deleted_but_a_new_one_with_the_same_screen_name_exists_sets_appropriate_status_attributes_on_the_new_channel.yml

Another idea was to use MD5 digests of the above,
but in fact both of these approaches share another problem:
even minor changes to the description could break tests
(unless the committer remembers to rename the cassette file to match):
an altered description means VCR will record a new cassette file
instead of replaying from the original.

(Normally, this would only slow down the test instead of breaking it,
but sometimes we modify tests and cassettes after recording them
to hide sensitive data like API keys or login credentials.)

The approach taken by this commit was to use partial descriptions,
combining the parent `describe`/`context` label with the `it` label.
This does not guarantee uniqueness--
even in the present refactoring, it produced a filename collision--
but it's a good middle ground.

[0]: https://relishapp.com/vcr/vcr/docs
This commit is contained in:
Ryan Lue 2019-11-12 16:17:21 +08:00 committed by Thorsten Eckel
parent 6d684c74cf
commit 1ebddff95f
36 changed files with 14220 additions and 113 deletions

View file

@ -3,7 +3,7 @@ require 'rails_helper'
RSpec.describe Import::Exchange::Folder do RSpec.describe Import::Exchange::Folder do
# see https://github.com/zammad/zammad/issues/2152 # see https://github.com/zammad/zammad/issues/2152
describe '#display_path (#2152)' do describe '#display_path (#2152)', :use_vcr do
let(:subject) { described_class.new(ews_connection) } let(:subject) { described_class.new(ews_connection) }
let(:ews_connection) { Viewpoint::EWSClient.new(endpoint, user, pass) } let(:ews_connection) { Viewpoint::EWSClient.new(endpoint, user, pass) }
let(:endpoint) { 'https://exchange.example.com/EWS/Exchange.asmx' } let(:endpoint) { 'https://exchange.example.com/EWS/Exchange.asmx' }
@ -12,11 +12,6 @@ RSpec.describe Import::Exchange::Folder do
let(:grandchild_of_root) { ews_connection.get_folder_by_name('Inbox') } let(:grandchild_of_root) { ews_connection.get_folder_by_name('Inbox') }
let(:child_of_root) { ews_connection.get_folder(grandchild_of_root.parent_folder_id) } let(:child_of_root) { ews_connection.get_folder(grandchild_of_root.parent_folder_id) }
around do |example|
cassette_name = example.description.gsub(/[^0-9A-Za-z.\-]+/, '_')
VCR.use_cassette("lib/import/exchange/folder/#{cassette_name}") { example.run }
end
context 'when server returns valid UTF-8' do context 'when server returns valid UTF-8' do
context 'and target folder is in root directory' do context 'and target folder is in root directory' do
it 'returns the display name of the folder' do it 'returns the display name of the folder' do

View file

@ -1,17 +1,11 @@
require 'rails_helper' require 'rails_helper'
RSpec.describe Channel do RSpec.describe Channel do
describe '#fetch' do describe '#fetch', use_vcr: :with_oauth_headers do
around do |example|
VCR.use_cassette(cassette, match_requests_on: %i[method uri oauth_headers]) { example.run }
end
context 'for Twitter driver' do context 'for Twitter driver' do
subject(:twitter_channel) { create(:twitter_channel) } subject(:twitter_channel) { create(:twitter_channel) }
context 'with invalid token' do context 'with invalid token' do
let(:cassette) { 'models/channel/driver/twitter/fetch_channel_invalid' }
it 'returns false' do it 'returns false' do
expect(twitter_channel.fetch(true)).to be(false) expect(twitter_channel.fetch(true)).to be(false)
end end
@ -30,8 +24,6 @@ RSpec.describe Channel do
end end
context 'with valid token' do context 'with valid token' do
let(:cassette) { 'models/channel/driver/twitter/fetch_channel_valid' }
it 'returns true' do it 'returns true' do
expect(twitter_channel.fetch(true)).to be(true) expect(twitter_channel.fetch(true)).to be(true)
end end

View file

@ -299,20 +299,11 @@ RSpec.describe Ticket::Article, type: :model do
end end
end end
describe 'Auto-setting of outgoing Twitter article attributes (via bg jobs):' do describe 'Auto-setting of outgoing Twitter article attributes (via bg jobs):', use_vcr: :with_oauth_headers do
subject!(:twitter_article) { create(:twitter_article, sender_name: 'Agent') } subject!(:twitter_article) { create(:twitter_article, sender_name: 'Agent') }
let(:channel) { Channel.find(twitter_article.ticket.preferences[:channel_id]) } let(:channel) { Channel.find(twitter_article.ticket.preferences[:channel_id]) }
let(:run_bg_jobs) { -> { Scheduler.worker(true) } }
let(:run_bg_jobs) do
lambda do
VCR.use_cassette(cassette, match_requests_on: %i[method uri oauth_headers]) do
Scheduler.worker(true)
end
end
end
let(:cassette) { 'models/channel/driver/twitter/article_to_tweet' }
it 'sets #from to senders Twitter handle' do it 'sets #from to senders Twitter handle' do
expect(&run_bg_jobs) expect(&run_bg_jobs)
@ -382,7 +373,6 @@ RSpec.describe Ticket::Article, type: :model do
context 'when the original channel (specified in ticket.preferences) was deleted' do context 'when the original channel (specified in ticket.preferences) was deleted' do
context 'but a new one with the same screen_name exists' do context 'but a new one with the same screen_name exists' do
let(:cassette) { 'models/channel/driver/twitter/article_to_tweet_channel_replace' }
let(:new_channel) { create(:twitter_channel) } let(:new_channel) { create(:twitter_channel) }
before do before do

View file

@ -89,10 +89,8 @@ RSpec.describe 'External Credentials', type: :request do
end end
context 'with invalid credentials, via request params' do context 'with invalid credentials, via request params' do
it 'returns 200 with remote (Facebook auth) error' do it 'returns 200 with remote (Facebook auth) error', :use_vcr do
VCR.use_cassette('request/external_credentials/facebook/app_verify_invalid_credentials_with_not_created') do post '/api/v1/external_credentials/facebook/app_verify', params: invalid_credentials, as: :json
post '/api/v1/external_credentials/facebook/app_verify', params: invalid_credentials, as: :json
end
expect(response).to have_http_status(:ok) expect(response).to have_http_status(:ok)
expect(json_response).to include('error' => 'type: OAuthException, code: 101, message: Error validating application. Cannot get application info due to a system error. [HTTP 400]') expect(json_response).to include('error' => 'type: OAuthException, code: 101, message: Error validating application. Cannot get application info due to a system error. [HTTP 400]')
@ -102,10 +100,8 @@ RSpec.describe 'External Credentials', type: :request do
context 'with invalid credentials, via ExternalCredential record' do context 'with invalid credentials, via ExternalCredential record' do
before { create(:facebook_credential, credentials: invalid_credentials) } before { create(:facebook_credential, credentials: invalid_credentials) }
it 'returns 200 with remote (Facebook auth) error' do it 'returns 200 with remote (Facebook auth) error', :use_vcr do
VCR.use_cassette('request/external_credentials/facebook/app_verify_invalid_credentials_with_created') do post '/api/v1/external_credentials/facebook/app_verify', as: :json
post '/api/v1/external_credentials/facebook/app_verify', as: :json
end
expect(response).to have_http_status(:ok) expect(response).to have_http_status(:ok)
expect(json_response).to include('error' => 'type: OAuthException, code: 101, message: Error validating application. Cannot get application info due to a system error. [HTTP 400]') expect(json_response).to include('error' => 'type: OAuthException, code: 101, message: Error validating application. Cannot get application info due to a system error. [HTTP 400]')
@ -137,10 +133,8 @@ RSpec.describe 'External Credentials', type: :request do
context 'with invalid credentials, via ExternalCredential record' do context 'with invalid credentials, via ExternalCredential record' do
before { create(:facebook_credential, credentials: invalid_credentials) } before { create(:facebook_credential, credentials: invalid_credentials) }
it 'returns 500 with remote (Facebook auth) error' do it 'returns 500 with remote (Facebook auth) error', :use_vcr do
VCR.use_cassette('request/external_credentials/facebook/link_account_with_invalid_credential') do get '/api/v1/external_credentials/facebook/link_account', as: :json
get '/api/v1/external_credentials/facebook/link_account', as: :json
end
expect(response).to have_http_status(:internal_server_error) expect(response).to have_http_status(:internal_server_error)
expect(json_response).to include('error' => 'type: OAuthException, code: 101, message: Error validating application. Cannot get application info due to a system error. [HTTP 400]') expect(json_response).to include('error' => 'type: OAuthException, code: 101, message: Error validating application. Cannot get application info due to a system error. [HTTP 400]')
@ -172,10 +166,8 @@ RSpec.describe 'External Credentials', type: :request do
context 'with invalid credentials, via ExternalCredential record' do context 'with invalid credentials, via ExternalCredential record' do
before { create(:facebook_credential, credentials: invalid_credentials) } before { create(:facebook_credential, credentials: invalid_credentials) }
it 'returns 500 with remote (Facebook auth) error' do it 'returns 500 with remote (Facebook auth) error', :use_vcr do
VCR.use_cassette('request/external_credentials/facebook/callback_invalid_credentials') do get '/api/v1/external_credentials/facebook/callback', as: :json
get '/api/v1/external_credentials/facebook/callback', as: :json
end
expect(response).to have_http_status(:internal_server_error) expect(response).to have_http_status(:internal_server_error)
expect(json_response).to include('error' => 'type: OAuthException, code: 101, message: Error validating application. Cannot get application info due to a system error. [HTTP 400]') expect(json_response).to include('error' => 'type: OAuthException, code: 101, message: Error validating application. Cannot get application info due to a system error. [HTTP 400]')
@ -212,10 +204,8 @@ RSpec.describe 'External Credentials', type: :request do
end end
context 'with invalid credentials, via request params' do context 'with invalid credentials, via request params' do
it 'returns 200 with remote (Twitter auth) error' do it 'returns 200 with remote (Twitter auth) error', :use_vcr do
VCR.use_cassette('request/external_credentials/twitter/app_verify_invalid_credentials_with_not_created') do post '/api/v1/external_credentials/twitter/app_verify', params: invalid_credentials, as: :json
post '/api/v1/external_credentials/twitter/app_verify', params: invalid_credentials, as: :json
end
expect(response).to have_http_status(:ok) expect(response).to have_http_status(:ok)
expect(json_response).to include('error' => '401 Authorization Required') expect(json_response).to include('error' => '401 Authorization Required')
@ -225,10 +215,8 @@ RSpec.describe 'External Credentials', type: :request do
context 'with invalid credentials, via existing ExternalCredential record' do context 'with invalid credentials, via existing ExternalCredential record' do
before { create(:twitter_credential, credentials: invalid_credentials) } before { create(:twitter_credential, credentials: invalid_credentials) }
it 'returns 200 with remote (Twitter auth) error' do it 'returns 200 with remote (Twitter auth) error', :use_vcr do
VCR.use_cassette('request/external_credentials/twitter/app_verify_invalid_credentials_with_created') do post '/api/v1/external_credentials/twitter/app_verify', as: :json
post '/api/v1/external_credentials/twitter/app_verify', as: :json
end
expect(response).to have_http_status(:ok) expect(response).to have_http_status(:ok)
expect(json_response).to include('error' => '401 Authorization Required') expect(json_response).to include('error' => '401 Authorization Required')
@ -260,10 +248,8 @@ RSpec.describe 'External Credentials', type: :request do
context 'with invalid credentials, via ExternalCredential record' do context 'with invalid credentials, via ExternalCredential record' do
before { create(:twitter_credential, credentials: invalid_credentials) } before { create(:twitter_credential, credentials: invalid_credentials) }
it 'returns 500 with remote (Twitter auth) error' do it 'returns 500 with remote (Twitter auth) error', :use_vcr do
VCR.use_cassette('request/external_credentials/twitter/link_account_with_invalid_credential') do get '/api/v1/external_credentials/twitter/link_account', as: :json
get '/api/v1/external_credentials/twitter/link_account', as: :json
end
expect(response).to have_http_status(:internal_server_error) expect(response).to have_http_status(:internal_server_error)
expect(json_response).to include('error' => '401 Authorization Required') expect(json_response).to include('error' => '401 Authorization Required')

View file

@ -19,3 +19,21 @@ VCR.configure do |config|
r2.headers['Authorization']&.map(&without_onetime_oauth_params) r2.headers['Authorization']&.map(&without_onetime_oauth_params)
end end
end end
RSpec.configure do |config|
config.around(:each, use_vcr: true) do |example|
spec_path = Pathname.new(example.file_path).realpath
cassette_path = spec_path.relative_path_from(Rails.root.join('spec')).sub(/_spec\.rb$/, '')
cassette_name = "#{example.example_group.description} #{example.description}".gsub(/[^0-9A-Za-z.\-]+/, '_').downcase
request_profile = case example.metadata[:use_vcr]
when true
%i[method uri]
when :with_oauth_headers
%i[method uri oauth_headers]
end
VCR.use_cassette(cassette_path.join(cassette_name), match_requests_on: request_profile) do
example.run
end
end
end

View file

@ -0,0 +1,51 @@
---
http_interactions:
- request:
method: get
uri: https://api.twitter.com/1.1/search/tweets.json?count=100&q=zammad&result_type=mixed
body:
encoding: UTF-8
string: ''
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="b5b77e1667355db2efc64e178b8a0aaa",
oauth_signature="tybPhlz3I5fMRF5%2BE12Pwx3U5XM%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543796201", oauth_token="key", oauth_version="1.0"
Connection:
- close
Host:
- api.twitter.com
response:
status:
code: 401
message: Unauthorized
headers:
Connection:
- close
Content-Length:
- '62'
Content-Type:
- application/json; charset=utf-8
Date:
- Mon, 03 Dec 2018 00:16:41 GMT
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379620109191613; Expires=Wed, 02 Dec 2020 00:16:41 GMT; Path=/;
Domain=.twitter.com
- personalization_id="v1_i2UDOt8QXhYvnNAv90Q8jA=="; Expires=Wed, 02 Dec 2020
00:16:41 GMT; Path=/; Domain=.twitter.com
Strict-Transport-Security:
- max-age=631138519
X-Connection-Hash:
- 8af740bd8d5f98022086657c7172b7ee
X-Response-Time:
- '114'
body:
encoding: UTF-8
string: '{"errors":[{"code":89,"message":"Invalid or expired token."}]}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:16:41 GMT
recorded_with: VCR 4.0.0

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -0,0 +1,87 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/1.1/statuses/update.json
body:
encoding: UTF-8
string: in_reply_to_status_id&status=Today+the+weather+is+really...
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="some",
oauth_signature="some%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543795610", oauth_token="key",
oauth_version="1.0"
Connection:
- close
Content-Type:
- application/x-www-form-urlencoded
Host:
- api.twitter.com
response:
status:
code: 200
message: OK
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Connection:
- close
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '2376'
Content-Type:
- application/json;charset=utf-8
Date:
- Mon, 03 Dec 2018 00:06:49 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Mon, 03 Dec 2018 00:06:49 GMT
Pragma:
- no-cache
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379560980468557; Expires=Wed, 02 Dec 2020 00:06:49 GMT; Path=/;
Domain=.twitter.com
- lang=en; Path=/
- personalization_id="v1_I6QHv6WAcEJj8qqGADKl+Q=="; Expires=Wed, 02 Dec 2020
00:06:49 GMT; Path=/; Domain=.twitter.com
Status:
- 200 OK
Strict-Transport-Security:
- max-age=631138519
X-Access-Level:
- read-write-directmessages
X-Connection-Hash:
- af3c2f4e24b6e6b940f913b84f710297
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '209'
X-Transaction:
- 00fb3d5400c70774
X-Tsa-Request-Body-Time:
- '0'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- 1; mode=block; report=https://twitter.com/i/xss_report
body:
encoding: UTF-8
string: '{"created_at":"Mon Dec 03 00:06:49 +0000 2018","id":1069382411899817990,"id_str":"1069382411899817990","text":"Today
the weather is really...","truncated":false,"entities":{"hashtags":[],"symbols":[],"user_mentions":[],"urls":[]},"source":"\u003ca
href=\"https:\/\/edenhofer.de\" rel=\"nofollow\"\u003eMartin Edenhofer\u003c\/a\u003e","in_reply_to_status_id":null,"in_reply_to_status_id_str":null,"in_reply_to_user_id":null,"in_reply_to_user_id_str":null,"in_reply_to_screen_name":null,"user":{"id":219826253,"id_str":"219826253","name":"Martin
Edenhofer","screen_name":"example","location":"","description":"Open Source
professional and geek. Also known as #OTRS and #Zammad inventor. ;)\r\nEntrepreneur
and Advisor for open source people in need.","url":"https:\/\/t.co\/whm4HTWdMw","entities":{"url":{"urls":[{"url":"https:\/\/t.co\/whm4HTWdMw","expanded_url":"http:\/\/edenhofer.de\/","display_url":"edenhofer.de","indices":[0,23]}]},"description":{"urls":[]}},"protected":false,"followers_count":311,"friends_count":314,"listed_count":16,"created_at":"Fri
Nov 26 00:19:49 +0000 2010","favourites_count":129,"utc_offset":null,"time_zone":null,"geo_enabled":false,"verified":false,"statuses_count":227,"lang":"en","contributors_enabled":false,"is_translator":false,"is_translation_enabled":false,"profile_background_color":"C0DEED","profile_background_image_url":"http:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_image_url_https":"https:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_tile":true,"profile_image_url":"http:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_image_url_https":"https:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_banner_url":"https:\/\/pbs.twimg.com\/profile_banners\/219826253\/1349428277","profile_link_color":"0084B4","profile_sidebar_border_color":"FFFFFF","profile_sidebar_fill_color":"DDEEF6","profile_text_color":"333333","profile_use_background_image":true,"has_extended_profile":false,"default_profile":false,"default_profile_image":false,"following":false,"follow_request_sent":false,"notifications":false,"translator_type":"regular"},"geo":null,"coordinates":null,"place":null,"contributors":null,"is_quote_status":false,"retweet_count":0,"favorite_count":0,"favorited":false,"retweeted":false,"lang":"en"}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:06:50 GMT
recorded_with: VCR 4.0.0

View file

@ -0,0 +1,87 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/1.1/statuses/update.json
body:
encoding: UTF-8
string: in_reply_to_status_id&status=Today+the+weather+is+really...
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="some",
oauth_signature="some%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543795610", oauth_token="key",
oauth_version="1.0"
Connection:
- close
Content-Type:
- application/x-www-form-urlencoded
Host:
- api.twitter.com
response:
status:
code: 200
message: OK
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Connection:
- close
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '2376'
Content-Type:
- application/json;charset=utf-8
Date:
- Mon, 03 Dec 2018 00:06:49 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Mon, 03 Dec 2018 00:06:49 GMT
Pragma:
- no-cache
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379560980468557; Expires=Wed, 02 Dec 2020 00:06:49 GMT; Path=/;
Domain=.twitter.com
- lang=en; Path=/
- personalization_id="v1_I6QHv6WAcEJj8qqGADKl+Q=="; Expires=Wed, 02 Dec 2020
00:06:49 GMT; Path=/; Domain=.twitter.com
Status:
- 200 OK
Strict-Transport-Security:
- max-age=631138519
X-Access-Level:
- read-write-directmessages
X-Connection-Hash:
- af3c2f4e24b6e6b940f913b84f710297
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '209'
X-Transaction:
- 00fb3d5400c70774
X-Tsa-Request-Body-Time:
- '0'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- 1; mode=block; report=https://twitter.com/i/xss_report
body:
encoding: UTF-8
string: '{"created_at":"Mon Dec 03 00:06:49 +0000 2018","id":1069382411899817990,"id_str":"1069382411899817990","text":"Today
the weather is really...","truncated":false,"entities":{"hashtags":[],"symbols":[],"user_mentions":[],"urls":[]},"source":"\u003ca
href=\"https:\/\/edenhofer.de\" rel=\"nofollow\"\u003eMartin Edenhofer\u003c\/a\u003e","in_reply_to_status_id":null,"in_reply_to_status_id_str":null,"in_reply_to_user_id":null,"in_reply_to_user_id_str":null,"in_reply_to_screen_name":null,"user":{"id":219826253,"id_str":"219826253","name":"Martin
Edenhofer","screen_name":"example","location":"","description":"Open Source
professional and geek. Also known as #OTRS and #Zammad inventor. ;)\r\nEntrepreneur
and Advisor for open source people in need.","url":"https:\/\/t.co\/whm4HTWdMw","entities":{"url":{"urls":[{"url":"https:\/\/t.co\/whm4HTWdMw","expanded_url":"http:\/\/edenhofer.de\/","display_url":"edenhofer.de","indices":[0,23]}]},"description":{"urls":[]}},"protected":false,"followers_count":311,"friends_count":314,"listed_count":16,"created_at":"Fri
Nov 26 00:19:49 +0000 2010","favourites_count":129,"utc_offset":null,"time_zone":null,"geo_enabled":false,"verified":false,"statuses_count":227,"lang":"en","contributors_enabled":false,"is_translator":false,"is_translation_enabled":false,"profile_background_color":"C0DEED","profile_background_image_url":"http:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_image_url_https":"https:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_tile":true,"profile_image_url":"http:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_image_url_https":"https:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_banner_url":"https:\/\/pbs.twimg.com\/profile_banners\/219826253\/1349428277","profile_link_color":"0084B4","profile_sidebar_border_color":"FFFFFF","profile_sidebar_fill_color":"DDEEF6","profile_text_color":"333333","profile_use_background_image":true,"has_extended_profile":false,"default_profile":false,"default_profile_image":false,"following":false,"follow_request_sent":false,"notifications":false,"translator_type":"regular"},"geo":null,"coordinates":null,"place":null,"contributors":null,"is_quote_status":false,"retweet_count":0,"favorite_count":0,"favorited":false,"retweeted":false,"lang":"en"}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:06:50 GMT
recorded_with: VCR 4.0.0

View file

@ -0,0 +1,87 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/1.1/statuses/update.json
body:
encoding: UTF-8
string: in_reply_to_status_id&status=Today+the+weather+is+really...
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="some",
oauth_signature="some%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543795610", oauth_token="key",
oauth_version="1.0"
Connection:
- close
Content-Type:
- application/x-www-form-urlencoded
Host:
- api.twitter.com
response:
status:
code: 200
message: OK
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Connection:
- close
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '2376'
Content-Type:
- application/json;charset=utf-8
Date:
- Mon, 03 Dec 2018 00:06:49 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Mon, 03 Dec 2018 00:06:49 GMT
Pragma:
- no-cache
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379560980468557; Expires=Wed, 02 Dec 2020 00:06:49 GMT; Path=/;
Domain=.twitter.com
- lang=en; Path=/
- personalization_id="v1_I6QHv6WAcEJj8qqGADKl+Q=="; Expires=Wed, 02 Dec 2020
00:06:49 GMT; Path=/; Domain=.twitter.com
Status:
- 200 OK
Strict-Transport-Security:
- max-age=631138519
X-Access-Level:
- read-write-directmessages
X-Connection-Hash:
- af3c2f4e24b6e6b940f913b84f710297
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '209'
X-Transaction:
- 00fb3d5400c70774
X-Tsa-Request-Body-Time:
- '0'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- 1; mode=block; report=https://twitter.com/i/xss_report
body:
encoding: UTF-8
string: '{"created_at":"Mon Dec 03 00:06:49 +0000 2018","id":1069382411899817990,"id_str":"1069382411899817990","text":"Today
the weather is really...","truncated":false,"entities":{"hashtags":[],"symbols":[],"user_mentions":[],"urls":[]},"source":"\u003ca
href=\"https:\/\/edenhofer.de\" rel=\"nofollow\"\u003eMartin Edenhofer\u003c\/a\u003e","in_reply_to_status_id":null,"in_reply_to_status_id_str":null,"in_reply_to_user_id":null,"in_reply_to_user_id_str":null,"in_reply_to_screen_name":null,"user":{"id":219826253,"id_str":"219826253","name":"Martin
Edenhofer","screen_name":"example","location":"","description":"Open Source
professional and geek. Also known as #OTRS and #Zammad inventor. ;)\r\nEntrepreneur
and Advisor for open source people in need.","url":"https:\/\/t.co\/whm4HTWdMw","entities":{"url":{"urls":[{"url":"https:\/\/t.co\/whm4HTWdMw","expanded_url":"http:\/\/edenhofer.de\/","display_url":"edenhofer.de","indices":[0,23]}]},"description":{"urls":[]}},"protected":false,"followers_count":311,"friends_count":314,"listed_count":16,"created_at":"Fri
Nov 26 00:19:49 +0000 2010","favourites_count":129,"utc_offset":null,"time_zone":null,"geo_enabled":false,"verified":false,"statuses_count":227,"lang":"en","contributors_enabled":false,"is_translator":false,"is_translation_enabled":false,"profile_background_color":"C0DEED","profile_background_image_url":"http:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_image_url_https":"https:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_tile":true,"profile_image_url":"http:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_image_url_https":"https:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_banner_url":"https:\/\/pbs.twimg.com\/profile_banners\/219826253\/1349428277","profile_link_color":"0084B4","profile_sidebar_border_color":"FFFFFF","profile_sidebar_fill_color":"DDEEF6","profile_text_color":"333333","profile_use_background_image":true,"has_extended_profile":false,"default_profile":false,"default_profile_image":false,"following":false,"follow_request_sent":false,"notifications":false,"translator_type":"regular"},"geo":null,"coordinates":null,"place":null,"contributors":null,"is_quote_status":false,"retweet_count":0,"favorite_count":0,"favorited":false,"retweeted":false,"lang":"en"}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:06:50 GMT
recorded_with: VCR 4.0.0

View file

@ -0,0 +1,87 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/1.1/statuses/update.json
body:
encoding: UTF-8
string: in_reply_to_status_id&status=Today+the+weather+is+really...
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="some",
oauth_signature="some%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543795610", oauth_token="key",
oauth_version="1.0"
Connection:
- close
Content-Type:
- application/x-www-form-urlencoded
Host:
- api.twitter.com
response:
status:
code: 200
message: OK
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Connection:
- close
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '2376'
Content-Type:
- application/json;charset=utf-8
Date:
- Mon, 03 Dec 2018 00:06:49 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Mon, 03 Dec 2018 00:06:49 GMT
Pragma:
- no-cache
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379560980468557; Expires=Wed, 02 Dec 2020 00:06:49 GMT; Path=/;
Domain=.twitter.com
- lang=en; Path=/
- personalization_id="v1_I6QHv6WAcEJj8qqGADKl+Q=="; Expires=Wed, 02 Dec 2020
00:06:49 GMT; Path=/; Domain=.twitter.com
Status:
- 200 OK
Strict-Transport-Security:
- max-age=631138519
X-Access-Level:
- read-write-directmessages
X-Connection-Hash:
- af3c2f4e24b6e6b940f913b84f710297
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '209'
X-Transaction:
- 00fb3d5400c70774
X-Tsa-Request-Body-Time:
- '0'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- 1; mode=block; report=https://twitter.com/i/xss_report
body:
encoding: UTF-8
string: '{"created_at":"Mon Dec 03 00:06:49 +0000 2018","id":1069382411899817990,"id_str":"1069382411899817990","text":"Today
the weather is really...","truncated":false,"entities":{"hashtags":[],"symbols":[],"user_mentions":[],"urls":[]},"source":"\u003ca
href=\"https:\/\/edenhofer.de\" rel=\"nofollow\"\u003eMartin Edenhofer\u003c\/a\u003e","in_reply_to_status_id":null,"in_reply_to_status_id_str":null,"in_reply_to_user_id":null,"in_reply_to_user_id_str":null,"in_reply_to_screen_name":null,"user":{"id":219826253,"id_str":"219826253","name":"Martin
Edenhofer","screen_name":"example","location":"","description":"Open Source
professional and geek. Also known as #OTRS and #Zammad inventor. ;)\r\nEntrepreneur
and Advisor for open source people in need.","url":"https:\/\/t.co\/whm4HTWdMw","entities":{"url":{"urls":[{"url":"https:\/\/t.co\/whm4HTWdMw","expanded_url":"http:\/\/edenhofer.de\/","display_url":"edenhofer.de","indices":[0,23]}]},"description":{"urls":[]}},"protected":false,"followers_count":311,"friends_count":314,"listed_count":16,"created_at":"Fri
Nov 26 00:19:49 +0000 2010","favourites_count":129,"utc_offset":null,"time_zone":null,"geo_enabled":false,"verified":false,"statuses_count":227,"lang":"en","contributors_enabled":false,"is_translator":false,"is_translation_enabled":false,"profile_background_color":"C0DEED","profile_background_image_url":"http:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_image_url_https":"https:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_tile":true,"profile_image_url":"http:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_image_url_https":"https:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_banner_url":"https:\/\/pbs.twimg.com\/profile_banners\/219826253\/1349428277","profile_link_color":"0084B4","profile_sidebar_border_color":"FFFFFF","profile_sidebar_fill_color":"DDEEF6","profile_text_color":"333333","profile_use_background_image":true,"has_extended_profile":false,"default_profile":false,"default_profile_image":false,"following":false,"follow_request_sent":false,"notifications":false,"translator_type":"regular"},"geo":null,"coordinates":null,"place":null,"contributors":null,"is_quote_status":false,"retweet_count":0,"favorite_count":0,"favorited":false,"retweeted":false,"lang":"en"}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:06:50 GMT
recorded_with: VCR 4.0.0

View file

@ -0,0 +1,87 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/1.1/statuses/update.json
body:
encoding: UTF-8
string: in_reply_to_status_id&status=Today+the+weather+is+really...
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="some",
oauth_signature="some%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543795610", oauth_token="key",
oauth_version="1.0"
Connection:
- close
Content-Type:
- application/x-www-form-urlencoded
Host:
- api.twitter.com
response:
status:
code: 200
message: OK
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Connection:
- close
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '2376'
Content-Type:
- application/json;charset=utf-8
Date:
- Mon, 03 Dec 2018 00:06:49 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Mon, 03 Dec 2018 00:06:49 GMT
Pragma:
- no-cache
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379560980468557; Expires=Wed, 02 Dec 2020 00:06:49 GMT; Path=/;
Domain=.twitter.com
- lang=en; Path=/
- personalization_id="v1_I6QHv6WAcEJj8qqGADKl+Q=="; Expires=Wed, 02 Dec 2020
00:06:49 GMT; Path=/; Domain=.twitter.com
Status:
- 200 OK
Strict-Transport-Security:
- max-age=631138519
X-Access-Level:
- read-write-directmessages
X-Connection-Hash:
- af3c2f4e24b6e6b940f913b84f710297
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '209'
X-Transaction:
- 00fb3d5400c70774
X-Tsa-Request-Body-Time:
- '0'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- 1; mode=block; report=https://twitter.com/i/xss_report
body:
encoding: UTF-8
string: '{"created_at":"Mon Dec 03 00:06:49 +0000 2018","id":1069382411899817990,"id_str":"1069382411899817990","text":"Today
the weather is really...","truncated":false,"entities":{"hashtags":[],"symbols":[],"user_mentions":[],"urls":[]},"source":"\u003ca
href=\"https:\/\/edenhofer.de\" rel=\"nofollow\"\u003eMartin Edenhofer\u003c\/a\u003e","in_reply_to_status_id":null,"in_reply_to_status_id_str":null,"in_reply_to_user_id":null,"in_reply_to_user_id_str":null,"in_reply_to_screen_name":null,"user":{"id":219826253,"id_str":"219826253","name":"Martin
Edenhofer","screen_name":"example","location":"","description":"Open Source
professional and geek. Also known as #OTRS and #Zammad inventor. ;)\r\nEntrepreneur
and Advisor for open source people in need.","url":"https:\/\/t.co\/whm4HTWdMw","entities":{"url":{"urls":[{"url":"https:\/\/t.co\/whm4HTWdMw","expanded_url":"http:\/\/edenhofer.de\/","display_url":"edenhofer.de","indices":[0,23]}]},"description":{"urls":[]}},"protected":false,"followers_count":311,"friends_count":314,"listed_count":16,"created_at":"Fri
Nov 26 00:19:49 +0000 2010","favourites_count":129,"utc_offset":null,"time_zone":null,"geo_enabled":false,"verified":false,"statuses_count":227,"lang":"en","contributors_enabled":false,"is_translator":false,"is_translation_enabled":false,"profile_background_color":"C0DEED","profile_background_image_url":"http:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_image_url_https":"https:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_tile":true,"profile_image_url":"http:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_image_url_https":"https:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_banner_url":"https:\/\/pbs.twimg.com\/profile_banners\/219826253\/1349428277","profile_link_color":"0084B4","profile_sidebar_border_color":"FFFFFF","profile_sidebar_fill_color":"DDEEF6","profile_text_color":"333333","profile_use_background_image":true,"has_extended_profile":false,"default_profile":false,"default_profile_image":false,"following":false,"follow_request_sent":false,"notifications":false,"translator_type":"regular"},"geo":null,"coordinates":null,"place":null,"contributors":null,"is_quote_status":false,"retweet_count":0,"favorite_count":0,"favorited":false,"retweeted":false,"lang":"en"}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:06:50 GMT
recorded_with: VCR 4.0.0

View file

@ -0,0 +1,87 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/1.1/statuses/update.json
body:
encoding: UTF-8
string: in_reply_to_status_id&status=Today+the+weather+is+really...
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="some",
oauth_signature="some%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543795610", oauth_token="key",
oauth_version="1.0"
Connection:
- close
Content-Type:
- application/x-www-form-urlencoded
Host:
- api.twitter.com
response:
status:
code: 200
message: OK
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Connection:
- close
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '2376'
Content-Type:
- application/json;charset=utf-8
Date:
- Mon, 03 Dec 2018 00:06:49 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Mon, 03 Dec 2018 00:06:49 GMT
Pragma:
- no-cache
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379560980468557; Expires=Wed, 02 Dec 2020 00:06:49 GMT; Path=/;
Domain=.twitter.com
- lang=en; Path=/
- personalization_id="v1_I6QHv6WAcEJj8qqGADKl+Q=="; Expires=Wed, 02 Dec 2020
00:06:49 GMT; Path=/; Domain=.twitter.com
Status:
- 200 OK
Strict-Transport-Security:
- max-age=631138519
X-Access-Level:
- read-write-directmessages
X-Connection-Hash:
- af3c2f4e24b6e6b940f913b84f710297
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '209'
X-Transaction:
- 00fb3d5400c70774
X-Tsa-Request-Body-Time:
- '0'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- 1; mode=block; report=https://twitter.com/i/xss_report
body:
encoding: UTF-8
string: '{"created_at":"Mon Dec 03 00:06:49 +0000 2018","id":1069382411899817990,"id_str":"1069382411899817990","text":"Today
the weather is really...","truncated":false,"entities":{"hashtags":[],"symbols":[],"user_mentions":[],"urls":[]},"source":"\u003ca
href=\"https:\/\/edenhofer.de\" rel=\"nofollow\"\u003eMartin Edenhofer\u003c\/a\u003e","in_reply_to_status_id":null,"in_reply_to_status_id_str":null,"in_reply_to_user_id":null,"in_reply_to_user_id_str":null,"in_reply_to_screen_name":null,"user":{"id":219826253,"id_str":"219826253","name":"Martin
Edenhofer","screen_name":"example","location":"","description":"Open Source
professional and geek. Also known as #OTRS and #Zammad inventor. ;)\r\nEntrepreneur
and Advisor for open source people in need.","url":"https:\/\/t.co\/whm4HTWdMw","entities":{"url":{"urls":[{"url":"https:\/\/t.co\/whm4HTWdMw","expanded_url":"http:\/\/edenhofer.de\/","display_url":"edenhofer.de","indices":[0,23]}]},"description":{"urls":[]}},"protected":false,"followers_count":311,"friends_count":314,"listed_count":16,"created_at":"Fri
Nov 26 00:19:49 +0000 2010","favourites_count":129,"utc_offset":null,"time_zone":null,"geo_enabled":false,"verified":false,"statuses_count":227,"lang":"en","contributors_enabled":false,"is_translator":false,"is_translation_enabled":false,"profile_background_color":"C0DEED","profile_background_image_url":"http:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_image_url_https":"https:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_tile":true,"profile_image_url":"http:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_image_url_https":"https:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_banner_url":"https:\/\/pbs.twimg.com\/profile_banners\/219826253\/1349428277","profile_link_color":"0084B4","profile_sidebar_border_color":"FFFFFF","profile_sidebar_fill_color":"DDEEF6","profile_text_color":"333333","profile_use_background_image":true,"has_extended_profile":false,"default_profile":false,"default_profile_image":false,"following":false,"follow_request_sent":false,"notifications":false,"translator_type":"regular"},"geo":null,"coordinates":null,"place":null,"contributors":null,"is_quote_status":false,"retweet_count":0,"favorite_count":0,"favorited":false,"retweeted":false,"lang":"en"}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:06:50 GMT
recorded_with: VCR 4.0.0

View file

@ -0,0 +1,87 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/1.1/statuses/update.json
body:
encoding: UTF-8
string: in_reply_to_status_id&status=Today+the+weather+is+really...
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="some",
oauth_signature="some%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543795610", oauth_token="key",
oauth_version="1.0"
Connection:
- close
Content-Type:
- application/x-www-form-urlencoded
Host:
- api.twitter.com
response:
status:
code: 200
message: OK
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Connection:
- close
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '2376'
Content-Type:
- application/json;charset=utf-8
Date:
- Mon, 03 Dec 2018 00:06:49 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Mon, 03 Dec 2018 00:06:49 GMT
Pragma:
- no-cache
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379560980468557; Expires=Wed, 02 Dec 2020 00:06:49 GMT; Path=/;
Domain=.twitter.com
- lang=en; Path=/
- personalization_id="v1_I6QHv6WAcEJj8qqGADKl+Q=="; Expires=Wed, 02 Dec 2020
00:06:49 GMT; Path=/; Domain=.twitter.com
Status:
- 200 OK
Strict-Transport-Security:
- max-age=631138519
X-Access-Level:
- read-write-directmessages
X-Connection-Hash:
- af3c2f4e24b6e6b940f913b84f710297
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '209'
X-Transaction:
- 00fb3d5400c70774
X-Tsa-Request-Body-Time:
- '0'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- 1; mode=block; report=https://twitter.com/i/xss_report
body:
encoding: UTF-8
string: '{"created_at":"Mon Dec 03 00:06:49 +0000 2018","id":1069382411899817990,"id_str":"1069382411899817990","text":"Today
the weather is really...","truncated":false,"entities":{"hashtags":[],"symbols":[],"user_mentions":[],"urls":[]},"source":"\u003ca
href=\"https:\/\/edenhofer.de\" rel=\"nofollow\"\u003eMartin Edenhofer\u003c\/a\u003e","in_reply_to_status_id":null,"in_reply_to_status_id_str":null,"in_reply_to_user_id":null,"in_reply_to_user_id_str":null,"in_reply_to_screen_name":null,"user":{"id":219826253,"id_str":"219826253","name":"Martin
Edenhofer","screen_name":"example","location":"","description":"Open Source
professional and geek. Also known as #OTRS and #Zammad inventor. ;)\r\nEntrepreneur
and Advisor for open source people in need.","url":"https:\/\/t.co\/whm4HTWdMw","entities":{"url":{"urls":[{"url":"https:\/\/t.co\/whm4HTWdMw","expanded_url":"http:\/\/edenhofer.de\/","display_url":"edenhofer.de","indices":[0,23]}]},"description":{"urls":[]}},"protected":false,"followers_count":311,"friends_count":314,"listed_count":16,"created_at":"Fri
Nov 26 00:19:49 +0000 2010","favourites_count":129,"utc_offset":null,"time_zone":null,"geo_enabled":false,"verified":false,"statuses_count":227,"lang":"en","contributors_enabled":false,"is_translator":false,"is_translation_enabled":false,"profile_background_color":"C0DEED","profile_background_image_url":"http:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_image_url_https":"https:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_tile":true,"profile_image_url":"http:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_image_url_https":"https:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_banner_url":"https:\/\/pbs.twimg.com\/profile_banners\/219826253\/1349428277","profile_link_color":"0084B4","profile_sidebar_border_color":"FFFFFF","profile_sidebar_fill_color":"DDEEF6","profile_text_color":"333333","profile_use_background_image":true,"has_extended_profile":false,"default_profile":false,"default_profile_image":false,"following":false,"follow_request_sent":false,"notifications":false,"translator_type":"regular"},"geo":null,"coordinates":null,"place":null,"contributors":null,"is_quote_status":false,"retweet_count":0,"favorite_count":0,"favorited":false,"retweeted":false,"lang":"en"}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:06:50 GMT
recorded_with: VCR 4.0.0

View file

@ -0,0 +1,87 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/1.1/statuses/update.json
body:
encoding: UTF-8
string: in_reply_to_status_id&status=Today+the+weather+is+really...
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="some",
oauth_signature="some%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543795610", oauth_token="key",
oauth_version="1.0"
Connection:
- close
Content-Type:
- application/x-www-form-urlencoded
Host:
- api.twitter.com
response:
status:
code: 200
message: OK
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Connection:
- close
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '2376'
Content-Type:
- application/json;charset=utf-8
Date:
- Mon, 03 Dec 2018 00:06:49 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Mon, 03 Dec 2018 00:06:49 GMT
Pragma:
- no-cache
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379560980468557; Expires=Wed, 02 Dec 2020 00:06:49 GMT; Path=/;
Domain=.twitter.com
- lang=en; Path=/
- personalization_id="v1_I6QHv6WAcEJj8qqGADKl+Q=="; Expires=Wed, 02 Dec 2020
00:06:49 GMT; Path=/; Domain=.twitter.com
Status:
- 200 OK
Strict-Transport-Security:
- max-age=631138519
X-Access-Level:
- read-write-directmessages
X-Connection-Hash:
- af3c2f4e24b6e6b940f913b84f710297
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '209'
X-Transaction:
- 00fb3d5400c70774
X-Tsa-Request-Body-Time:
- '0'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- 1; mode=block; report=https://twitter.com/i/xss_report
body:
encoding: UTF-8
string: '{"created_at":"Mon Dec 03 00:06:49 +0000 2018","id":1069382411899817990,"id_str":"1069382411899817990","text":"Today
the weather is really...","truncated":false,"entities":{"hashtags":[],"symbols":[],"user_mentions":[],"urls":[]},"source":"\u003ca
href=\"https:\/\/edenhofer.de\" rel=\"nofollow\"\u003eMartin Edenhofer\u003c\/a\u003e","in_reply_to_status_id":null,"in_reply_to_status_id_str":null,"in_reply_to_user_id":null,"in_reply_to_user_id_str":null,"in_reply_to_screen_name":null,"user":{"id":219826253,"id_str":"219826253","name":"Martin
Edenhofer","screen_name":"example","location":"","description":"Open Source
professional and geek. Also known as #OTRS and #Zammad inventor. ;)\r\nEntrepreneur
and Advisor for open source people in need.","url":"https:\/\/t.co\/whm4HTWdMw","entities":{"url":{"urls":[{"url":"https:\/\/t.co\/whm4HTWdMw","expanded_url":"http:\/\/edenhofer.de\/","display_url":"edenhofer.de","indices":[0,23]}]},"description":{"urls":[]}},"protected":false,"followers_count":311,"friends_count":314,"listed_count":16,"created_at":"Fri
Nov 26 00:19:49 +0000 2010","favourites_count":129,"utc_offset":null,"time_zone":null,"geo_enabled":false,"verified":false,"statuses_count":227,"lang":"en","contributors_enabled":false,"is_translator":false,"is_translation_enabled":false,"profile_background_color":"C0DEED","profile_background_image_url":"http:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_image_url_https":"https:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_tile":true,"profile_image_url":"http:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_image_url_https":"https:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_banner_url":"https:\/\/pbs.twimg.com\/profile_banners\/219826253\/1349428277","profile_link_color":"0084B4","profile_sidebar_border_color":"FFFFFF","profile_sidebar_fill_color":"DDEEF6","profile_text_color":"333333","profile_use_background_image":true,"has_extended_profile":false,"default_profile":false,"default_profile_image":false,"following":false,"follow_request_sent":false,"notifications":false,"translator_type":"regular"},"geo":null,"coordinates":null,"place":null,"contributors":null,"is_quote_status":false,"retweet_count":0,"favorite_count":0,"favorited":false,"retweeted":false,"lang":"en"}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:06:50 GMT
recorded_with: VCR 4.0.0

View file

@ -0,0 +1,87 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/1.1/statuses/update.json
body:
encoding: UTF-8
string: in_reply_to_status_id&status=Today+the+weather+is+really...
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="some",
oauth_signature="some%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543795610", oauth_token="key",
oauth_version="1.0"
Connection:
- close
Content-Type:
- application/x-www-form-urlencoded
Host:
- api.twitter.com
response:
status:
code: 200
message: OK
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Connection:
- close
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '2376'
Content-Type:
- application/json;charset=utf-8
Date:
- Mon, 03 Dec 2018 00:06:49 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Mon, 03 Dec 2018 00:06:49 GMT
Pragma:
- no-cache
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379560980468557; Expires=Wed, 02 Dec 2020 00:06:49 GMT; Path=/;
Domain=.twitter.com
- lang=en; Path=/
- personalization_id="v1_I6QHv6WAcEJj8qqGADKl+Q=="; Expires=Wed, 02 Dec 2020
00:06:49 GMT; Path=/; Domain=.twitter.com
Status:
- 200 OK
Strict-Transport-Security:
- max-age=631138519
X-Access-Level:
- read-write-directmessages
X-Connection-Hash:
- af3c2f4e24b6e6b940f913b84f710297
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '209'
X-Transaction:
- 00fb3d5400c70774
X-Tsa-Request-Body-Time:
- '0'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- 1; mode=block; report=https://twitter.com/i/xss_report
body:
encoding: UTF-8
string: '{"created_at":"Mon Dec 03 00:06:49 +0000 2018","id":1069382411899817990,"id_str":"1069382411899817990","text":"Today
the weather is really...","truncated":false,"entities":{"hashtags":[],"symbols":[],"user_mentions":[],"urls":[]},"source":"\u003ca
href=\"https:\/\/edenhofer.de\" rel=\"nofollow\"\u003eMartin Edenhofer\u003c\/a\u003e","in_reply_to_status_id":null,"in_reply_to_status_id_str":null,"in_reply_to_user_id":null,"in_reply_to_user_id_str":null,"in_reply_to_screen_name":null,"user":{"id":219826253,"id_str":"219826253","name":"Martin
Edenhofer","screen_name":"example","location":"","description":"Open Source
professional and geek. Also known as #OTRS and #Zammad inventor. ;)\r\nEntrepreneur
and Advisor for open source people in need.","url":"https:\/\/t.co\/whm4HTWdMw","entities":{"url":{"urls":[{"url":"https:\/\/t.co\/whm4HTWdMw","expanded_url":"http:\/\/edenhofer.de\/","display_url":"edenhofer.de","indices":[0,23]}]},"description":{"urls":[]}},"protected":false,"followers_count":311,"friends_count":314,"listed_count":16,"created_at":"Fri
Nov 26 00:19:49 +0000 2010","favourites_count":129,"utc_offset":null,"time_zone":null,"geo_enabled":false,"verified":false,"statuses_count":227,"lang":"en","contributors_enabled":false,"is_translator":false,"is_translation_enabled":false,"profile_background_color":"C0DEED","profile_background_image_url":"http:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_image_url_https":"https:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_tile":true,"profile_image_url":"http:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_image_url_https":"https:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_banner_url":"https:\/\/pbs.twimg.com\/profile_banners\/219826253\/1349428277","profile_link_color":"0084B4","profile_sidebar_border_color":"FFFFFF","profile_sidebar_fill_color":"DDEEF6","profile_text_color":"333333","profile_use_background_image":true,"has_extended_profile":false,"default_profile":false,"default_profile_image":false,"following":false,"follow_request_sent":false,"notifications":false,"translator_type":"regular"},"geo":null,"coordinates":null,"place":null,"contributors":null,"is_quote_status":false,"retweet_count":0,"favorite_count":0,"favorited":false,"retweeted":false,"lang":"en"}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:06:50 GMT
recorded_with: VCR 4.0.0

View file

@ -0,0 +1,87 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/1.1/statuses/update.json
body:
encoding: UTF-8
string: in_reply_to_status_id&status=Today+the+weather+is+really...
headers:
User-Agent:
- TwitterRubyGem/6.2.0
Authorization:
- OAuth oauth_consumer_key="some", oauth_nonce="some",
oauth_signature="some%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1543795610", oauth_token="key",
oauth_version="1.0"
Connection:
- close
Content-Type:
- application/x-www-form-urlencoded
Host:
- api.twitter.com
response:
status:
code: 200
message: OK
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Connection:
- close
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '2376'
Content-Type:
- application/json;charset=utf-8
Date:
- Mon, 03 Dec 2018 00:06:49 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Mon, 03 Dec 2018 00:06:49 GMT
Pragma:
- no-cache
Server:
- tsa_o
Set-Cookie:
- guest_id=v1%3A154379560980468557; Expires=Wed, 02 Dec 2020 00:06:49 GMT; Path=/;
Domain=.twitter.com
- lang=en; Path=/
- personalization_id="v1_I6QHv6WAcEJj8qqGADKl+Q=="; Expires=Wed, 02 Dec 2020
00:06:49 GMT; Path=/; Domain=.twitter.com
Status:
- 200 OK
Strict-Transport-Security:
- max-age=631138519
X-Access-Level:
- read-write-directmessages
X-Connection-Hash:
- af3c2f4e24b6e6b940f913b84f710297
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '209'
X-Transaction:
- 00fb3d5400c70774
X-Tsa-Request-Body-Time:
- '0'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- 1; mode=block; report=https://twitter.com/i/xss_report
body:
encoding: UTF-8
string: '{"created_at":"Mon Dec 03 00:06:49 +0000 2018","id":1069382411899817990,"id_str":"1069382411899817990","text":"Today
the weather is really...","truncated":false,"entities":{"hashtags":[],"symbols":[],"user_mentions":[],"urls":[]},"source":"\u003ca
href=\"https:\/\/edenhofer.de\" rel=\"nofollow\"\u003eMartin Edenhofer\u003c\/a\u003e","in_reply_to_status_id":null,"in_reply_to_status_id_str":null,"in_reply_to_user_id":null,"in_reply_to_user_id_str":null,"in_reply_to_screen_name":null,"user":{"id":219826253,"id_str":"219826253","name":"Martin
Edenhofer","screen_name":"example","location":"","description":"Open Source
professional and geek. Also known as #OTRS and #Zammad inventor. ;)\r\nEntrepreneur
and Advisor for open source people in need.","url":"https:\/\/t.co\/whm4HTWdMw","entities":{"url":{"urls":[{"url":"https:\/\/t.co\/whm4HTWdMw","expanded_url":"http:\/\/edenhofer.de\/","display_url":"edenhofer.de","indices":[0,23]}]},"description":{"urls":[]}},"protected":false,"followers_count":311,"friends_count":314,"listed_count":16,"created_at":"Fri
Nov 26 00:19:49 +0000 2010","favourites_count":129,"utc_offset":null,"time_zone":null,"geo_enabled":false,"verified":false,"statuses_count":227,"lang":"en","contributors_enabled":false,"is_translator":false,"is_translation_enabled":false,"profile_background_color":"C0DEED","profile_background_image_url":"http:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_image_url_https":"https:\/\/abs.twimg.com\/images\/themes\/theme1\/bg.png","profile_background_tile":true,"profile_image_url":"http:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_image_url_https":"https:\/\/pbs.twimg.com\/profile_images\/794220000450150401\/D-eFg44R_normal.jpg","profile_banner_url":"https:\/\/pbs.twimg.com\/profile_banners\/219826253\/1349428277","profile_link_color":"0084B4","profile_sidebar_border_color":"FFFFFF","profile_sidebar_fill_color":"DDEEF6","profile_text_color":"333333","profile_use_background_image":true,"has_extended_profile":false,"default_profile":false,"default_profile_image":false,"following":false,"follow_request_sent":false,"notifications":false,"translator_type":"regular"},"geo":null,"coordinates":null,"place":null,"contributors":null,"is_quote_status":false,"retweet_count":0,"favorite_count":0,"favorited":false,"retweeted":false,"lang":"en"}'
http_version:
recorded_at: Mon, 03 Dec 2018 00:06:50 GMT
recorded_with: VCR 4.0.0

View file

@ -1,58 +0,0 @@
---
http_interactions:
- request:
method: post
uri: https://graph.facebook.com/oauth/access_token
body:
encoding: UTF-8
string: client_id=123&client_secret=123&grant_type=client_credentials
headers:
User-Agent:
- Faraday v0.12.2
Content-Type:
- application/x-www-form-urlencoded
Accept-Encoding:
- gzip;q=1.0,deflate;q=0.6,identity;q=0.3
Accept:
- "*/*"
response:
status:
code: 400
message: Bad Request
headers:
Www-Authenticate:
- OAuth "Facebook Platform" "invalid_client" "Error validating application.
Cannot get application info due to a system error."
Content-Type:
- application/json; charset=UTF-8
Facebook-Api-Version:
- v2.8
X-Fb-Rev:
- '4583987'
Access-Control-Allow-Origin:
- "*"
Cache-Control:
- no-store
X-Fb-Trace-Id:
- GHQfpOGoO6+
Expires:
- Sat, 01 Jan 2000 00:00:00 GMT
Strict-Transport-Security:
- max-age=15552000; preload
Pragma:
- no-cache
X-Fb-Debug:
- m45LKcljfKLk5t2vVVgXoLkxboPq32H2Byv20O+HYluzgxL562XCEFcUiEH2dyt9UOGMqoFUpYHSYJGaEnrxRA==
Date:
- Fri, 30 Nov 2018 12:50:47 GMT
Connection:
- keep-alive
Content-Length:
- '166'
body:
encoding: UTF-8
string: '{"error":{"message":"Error validating application. Cannot get application
info due to a system error.","type":"OAuthException","code":101,"fbtrace_id":"GHQfpOGoO6+"}}'
http_version:
recorded_at: Fri, 30 Nov 2018 12:50:47 GMT
recorded_with: VCR 4.0.0

View file

@ -1,5 +1,60 @@
--- ---
http_interactions: http_interactions:
- request:
method: post
uri: https://graph.facebook.com/oauth/access_token
body:
encoding: UTF-8
string: client_id=123&client_secret=123&grant_type=client_credentials
headers:
User-Agent:
- Faraday v0.12.2
Content-Type:
- application/x-www-form-urlencoded
Accept-Encoding:
- gzip;q=1.0,deflate;q=0.6,identity;q=0.3
Accept:
- "*/*"
response:
status:
code: 400
message: Bad Request
headers:
Www-Authenticate:
- OAuth "Facebook Platform" "invalid_client" "Error validating application.
Cannot get application info due to a system error."
Content-Type:
- application/json; charset=UTF-8
Facebook-Api-Version:
- v2.8
X-Fb-Rev:
- '4583987'
Access-Control-Allow-Origin:
- "*"
Cache-Control:
- no-store
X-Fb-Trace-Id:
- GHQfpOGoO6+
Expires:
- Sat, 01 Jan 2000 00:00:00 GMT
Strict-Transport-Security:
- max-age=15552000; preload
Pragma:
- no-cache
X-Fb-Debug:
- m45LKcljfKLk5t2vVVgXoLkxboPq32H2Byv20O+HYluzgxL562XCEFcUiEH2dyt9UOGMqoFUpYHSYJGaEnrxRA==
Date:
- Fri, 30 Nov 2018 12:50:47 GMT
Connection:
- keep-alive
Content-Length:
- '166'
body:
encoding: UTF-8
string: '{"error":{"message":"Error validating application. Cannot get application
info due to a system error.","type":"OAuthException","code":101,"fbtrace_id":"GHQfpOGoO6+"}}'
http_version:
recorded_at: Fri, 30 Nov 2018 12:50:47 GMT
- request: - request:
method: get method: get
uri: https://graph.facebook.com/oauth/access_token?client_id=123&client_secret=123&code&redirect_uri=http://zammad.example.com/api/v1/external_credentials/facebook/callback uri: https://graph.facebook.com/oauth/access_token?client_id=123&client_secret=123&code&redirect_uri=http://zammad.example.com/api/v1/external_credentials/facebook/callback

View file

@ -0,0 +1,76 @@
---
http_interactions:
- request:
method: post
uri: https://api.twitter.com/oauth/request_token
body:
encoding: UTF-8
string: ''
headers:
Accept-Encoding:
- gzip;q=1.0,deflate;q=0.6,identity;q=0.3
Accept:
- "*/*"
User-Agent:
- OAuth gem v0.5.4
Content-Length:
- '0'
Authorization:
- OAuth oauth_callback="http%3A%2F%2Fzammad.example.com%2Fapi%2Fv1%2Fexternal_credentials%2Ftwitter%2Fcallback",
oauth_consumer_key="123", oauth_nonce="f1YmStPaUKxHSrCJCbN4LEBvGhjPs41P9rFzOrnhqc",
oauth_signature="mPMYvS8A4FiTPhxPDlFB%2FGF0X2U%3D", oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1573570318", oauth_version="1.0"
response:
status:
code: 401
message: Authorization Required
headers:
Cache-Control:
- no-cache, no-store, must-revalidate, pre-check=0, post-check=0
Content-Disposition:
- attachment; filename=json.json
Content-Length:
- '89'
Content-Type:
- application/json; charset=utf-8
Date:
- Tue, 12 Nov 2019 14:51:59 GMT
Expires:
- Tue, 31 Mar 1981 05:00:00 GMT
Last-Modified:
- Tue, 12 Nov 2019 14:51:58 GMT
Pragma:
- no-cache
Server:
- tsa_m
Set-Cookie:
- guest_id=v1%3A157357031898209376; Max-Age=63072000; Expires=Thu, 11 Nov 2021
14:51:58 GMT; Path=/; Domain=.twitter.com
- personalization_id="v1_jB1SWZRvZIk1S63ok8jVog=="; Max-Age=63072000; Expires=Thu,
11 Nov 2021 14:51:58 GMT; Path=/; Domain=.twitter.com
Status:
- 401 Unauthorized
Strict-Transport-Security:
- max-age=631138519
Www-Authenticate:
- OAuth realm="https://api.twitter.com"
X-Connection-Hash:
- a4ba44ed62e7eb6cb9503b492304013e
X-Content-Type-Options:
- nosniff
X-Frame-Options:
- SAMEORIGIN
X-Response-Time:
- '103'
X-Transaction:
- '009c9ec5003d9011'
X-Twitter-Response-Tags:
- BouncerCompliant
X-Xss-Protection:
- '0'
body:
encoding: ASCII-8BIT
string: '{"errors":[{"code":32,"message":"Could not authenticate you."}]}'
http_version:
recorded_at: Tue, 12 Nov 2019 14:51:59 GMT
recorded_with: VCR 4.0.0