mirror of
https://github.com/Retrospring/retrospring.git
synced 2025-02-13 21:33:20 +01:00
Merge pull request #227 from Retrospring/fix/tweet-length
Fixes to ensure answers shared to twitter post more reliably
This commit is contained in:
commit
c773d43447
9 changed files with 89 additions and 18 deletions
|
@ -12,9 +12,10 @@ RUN curl -sL https://deb.nodesource.com/setup_12.x | bash -
|
|||
|
||||
RUN apt-get update -qq \
|
||||
&& apt-get install -y --no-install-recommends build-essential \
|
||||
libpq-dev postgresql-client \
|
||||
libpq-dev postgresql-client \
|
||||
libxml2-dev libxslt1-dev \
|
||||
libmagickwand-dev imagemagick \
|
||||
libidn11-dev \
|
||||
nodejs \
|
||||
yarn \
|
||||
&& rm -rf /var/lib/apt/lists/*
|
||||
|
|
2
.github/workflows/retrospring.yml
vendored
2
.github/workflows/retrospring.yml
vendored
|
@ -52,7 +52,7 @@ jobs:
|
|||
with:
|
||||
node-version: '12'
|
||||
- name: Install dependencies
|
||||
run: sudo apt update && sudo apt-get install -y libpq-dev libxml2-dev libxslt1-dev libmagickwand-dev imagemagick
|
||||
run: sudo apt update && sudo apt-get install -y libpq-dev libxml2-dev libxslt1-dev libmagickwand-dev imagemagick libidn11-dev
|
||||
- name: Copy default configuration
|
||||
run: |
|
||||
cp config/database.yml.postgres config/database.yml
|
||||
|
|
1
Gemfile
1
Gemfile
|
@ -57,6 +57,7 @@ gem 'omniauth-tumblr'
|
|||
|
||||
# OAuth clients
|
||||
gem 'twitter'
|
||||
gem 'twitter-text'
|
||||
# To use a more recent Faraday version, a fork of this gem is required.
|
||||
gem 'tumblr_client', git: 'https://github.com/amplifr/tumblr_client'
|
||||
|
||||
|
|
|
@ -251,6 +251,7 @@ GEM
|
|||
concurrent-ruby (~> 1.0)
|
||||
i18n-js (3.6.0)
|
||||
i18n (>= 0.6.6)
|
||||
idn-ruby (0.1.4)
|
||||
image_processing (1.12.1)
|
||||
mini_magick (>= 4.9.5, < 5)
|
||||
ruby-vips (>= 2.0.17, < 3)
|
||||
|
@ -534,6 +535,9 @@ GEM
|
|||
multipart-post (~> 2.0)
|
||||
naught (~> 1.0)
|
||||
simple_oauth (~> 0.3.0)
|
||||
twitter-text (3.1.0)
|
||||
idn-ruby
|
||||
unf (~> 0.1.0)
|
||||
tzinfo (1.2.9)
|
||||
thread_safe (~> 0.1)
|
||||
uglifier (4.2.0)
|
||||
|
@ -632,6 +636,7 @@ DEPENDENCIES
|
|||
tumblr_client!
|
||||
turbolinks (~> 2.5.3)
|
||||
twitter
|
||||
twitter-text
|
||||
uglifier (>= 1.3.0)
|
||||
web-console (< 4.0.0)
|
||||
webpacker (~> 5.2)
|
||||
|
|
|
@ -48,7 +48,9 @@ class Ajax::AnswerController < AjaxController
|
|||
end
|
||||
|
||||
services = JSON.parse params[:share]
|
||||
ShareWorker.perform_async(current_user.id, answer.id, services)
|
||||
services.each do |service|
|
||||
ShareWorker.perform_async(current_user.id, answer.id, service)
|
||||
end
|
||||
|
||||
|
||||
@response[:status] = :okay
|
||||
|
|
|
@ -27,16 +27,30 @@ class Services::Twitter < Service
|
|||
end
|
||||
|
||||
def prepare_tweet(answer)
|
||||
# TODO: improve this.
|
||||
question_content = twitter_markdown answer.question.content.gsub(/\@(\w+)/, '\1')
|
||||
original_question_length = question_content.length
|
||||
answer_content = twitter_markdown answer.content
|
||||
original_answer_length = answer_content.length
|
||||
answer_url = show_user_answer_url(
|
||||
id: answer.id,
|
||||
username: answer.user.screen_name,
|
||||
host: APP_CONFIG['hostname'],
|
||||
protocol: (APP_CONFIG['https'] ? :https : :http)
|
||||
)
|
||||
"#{question_content[0..122]}#{'…' if question_content.length > 123}" \
|
||||
" — #{answer_content[0..123]}#{'…' if answer_content.length > 124} #{answer_url}"
|
||||
|
||||
parsed_tweet = { :valid => false }
|
||||
tweet_text = ""
|
||||
|
||||
until parsed_tweet[:valid]
|
||||
tweet_text = "#{question_content[0..122]}#{'…' if original_question_length > [123, question_content.length].min}" \
|
||||
" — #{answer_content[0..123]}#{'…' if original_answer_length > [124, answer_content.length].min} #{answer_url}"
|
||||
|
||||
parsed_tweet = Twitter::TwitterText::Validation::parse_tweet(tweet_text)
|
||||
|
||||
question_content = question_content[0..-2]
|
||||
answer_content = answer_content[0..-2]
|
||||
end
|
||||
|
||||
tweet_text
|
||||
end
|
||||
end
|
||||
|
|
|
@ -1,19 +1,19 @@
|
|||
class ShareWorker
|
||||
include Sidekiq::Worker
|
||||
|
||||
sidekiq_options queue: :share, retry: false
|
||||
sidekiq_options queue: :share, retry: 5
|
||||
|
||||
# @param user_id [Integer] the user id
|
||||
# @param answer_id [Integer] the user id
|
||||
# @param services [Array] array containing strings
|
||||
def perform(user_id, answer_id, services)
|
||||
User.find(user_id).services.each do |service|
|
||||
begin
|
||||
service.post(Answer.find(answer_id)) if services.include? service.provider
|
||||
rescue => e
|
||||
logger.info "failed to post answer #{answer_id} to #{service.provider} for user #{user_id}: #{e.message}"
|
||||
NewRelic::Agent.notice_error(e)
|
||||
end
|
||||
end
|
||||
# @param service [String] the service to post to
|
||||
def perform(user_id, answer_id, service)
|
||||
service_type = "Services::#{service.camelize}"
|
||||
user_service = User.find(user_id).services.find_by(type: service_type)
|
||||
|
||||
user_service.post(Answer.find(answer_id))
|
||||
rescue => e
|
||||
logger.info "failed to post answer #{answer_id} to #{service.provider} for user #{user_id}: #{e.message}"
|
||||
NewRelic::Agent.notice_error(e)
|
||||
raise
|
||||
end
|
||||
end
|
||||
|
|
|
@ -27,7 +27,9 @@ describe Ajax::AnswerController, :ajax_controller, type: :controller do
|
|||
|
||||
it "enqueues a job for sharing the answer to social networks" do
|
||||
subject
|
||||
expect(ShareWorker).to have_enqueued_sidekiq_job(user.id, Answer.last.id, shared_services)
|
||||
shared_services.each do |service|
|
||||
expect(ShareWorker).to have_enqueued_sidekiq_job(user.id, Answer.last.id, service)
|
||||
end
|
||||
end
|
||||
|
||||
include_examples "returns the expected response"
|
||||
|
|
46
spec/models/services/twitter_spec.rb
Normal file
46
spec/models/services/twitter_spec.rb
Normal file
|
@ -0,0 +1,46 @@
|
|||
# frozen_string_literal: true
|
||||
|
||||
require 'rails_helper'
|
||||
|
||||
describe Services::Twitter do
|
||||
describe "#post" do
|
||||
let(:user) { FactoryBot.create(:user) }
|
||||
let(:service) { Services::Twitter.create(user: user) }
|
||||
let(:answer) { FactoryBot.create(:answer, user: user,
|
||||
content: 'a' * 255,
|
||||
question_content: 'q' * 255) }
|
||||
let(:twitter_client) { instance_double(Twitter::REST::Client) }
|
||||
|
||||
before do
|
||||
allow(Twitter::REST::Client).to receive(:new).and_return(twitter_client)
|
||||
allow(twitter_client).to receive(:update!)
|
||||
stub_const("APP_CONFIG", {
|
||||
'hostname' => 'example.com',
|
||||
'https' => true,
|
||||
'items_per_page' => 5,
|
||||
'sharing' => {
|
||||
'twitter' => {
|
||||
'consumer_key' => 'AAA',
|
||||
}
|
||||
}
|
||||
})
|
||||
end
|
||||
|
||||
it "posts a shortened tweet" do
|
||||
service.post(answer)
|
||||
|
||||
expect(twitter_client).to have_received(:update!).with("#{'q' * 123}… — #{'a' * 124}… https://example.com/#{user.screen_name}/a/#{answer.id}")
|
||||
end
|
||||
|
||||
it "posts an un-shortened tweet" do
|
||||
answer.question.content = 'Why are raccoons so good?'
|
||||
answer.question.save!
|
||||
answer.content = 'Because they are good cunes.'
|
||||
answer.save!
|
||||
|
||||
service.post(answer)
|
||||
|
||||
expect(twitter_client).to have_received(:update!).with("#{answer.question.content} — #{answer.content} https://example.com/#{user.screen_name}/a/#{answer.id}")
|
||||
end
|
||||
end
|
||||
end
|
Loading…
Reference in a new issue