Instantly share code, notes, and snippets.

Embed
What would you like to do?
Daily Dilbert widget for Dashing

Description

This is Dashing widget and all components needed to retrieve, store and show daily strips from Dilbert. It is inspired by RandomAww widget.

##Usage

The latest version of this widget needs my slightly improved standard image widget. Put the daily_dilbert.rb file in your /jobs folder.

Make sure directory /assets/images/daily_dilbert is created and accessible by Dashing user.

To include the widget in a dashboard, add the following snippet to the dashboard layout file:

<li data-row="1" data-col="1" data-sizex="3" data-sizey="1">
  <div data-id="daily_dilbert" data-view="Image" data-width="100%"></div>
</li>

##Settings

Widget is made to support proxy server. If you have one, specify its url in PROXY in /jobs/daily_dilbert.rb.

To minimize requests to strip web site daily strip is downloaded once a day at 7:00. The same scheduler task used to download image and show the same image on dashboard until 11:00 when another scheduler job starts and cycles through all existing image files in /assets/images/daily_dilbert. The list of images is ordered by name (name is date) and then reversed to see newest strips first. By default, strip is rotated every 15 minutes. Please amend parameters if needed. I think, source code is self explanatory ;).

The every 15 minute job is unscheduled ~6:00 to avoid collision with strip downloader job.

require 'net/http'
require 'chronic'
class DailyDilbert
# Proxy URL - e.g. "http://127.1.1.1:8080/"
PROXY = ""
DATE_FORMAT = '%Y%m%d'
STRIP_DIR = "assets/images/daily_dilbert"
STRIP_PATTERN = STRIP_DIR+"/"+DATE_FORMAT+".gif"
attr_accessor :currentStrip
def get_strip_url
proxyURI = URI.parse(PROXY)
# old http = Net::HTTP.new('www.dilbert.com', nil, proxyURI.host, proxyURI.port)
http = Net::HTTP.new('dilbert.com', nil, proxyURI.host, proxyURI.port)
# old response = http.request(Net::HTTP::Get.new('/fast'))
response = http.request(Net::HTTP::Get.new('/'))
# old response.body.scan(/<img src=\"(\/dyn\/str\_strip\/[\/0-9]*\.strip\.print\.gif)\" \/>/)[0][0] if response and response.body
response.body.scan(/<img[^>]*src=\"http:\/\/assets\.amuniversal\.com\/([a-zA-Z0-9]+)\"[^>]*\/?>/)[0][0] if response and response.body
end
def download_strip(url)
proxyURI = URI.parse(PROXY)
file_name = DateTime.now.strftime(STRIP_PATTERN)
FileUtils.mkdir_p STRIP_DIR if not File.directory?(STRIP_DIR)
# old Net::HTTP.start('www.dilbert.com', nil, proxyURI.host, proxyURI.port) { |http|
Net::HTTP.start('assets.amuniversal.com', nil, proxyURI.host, proxyURI.port) { |http|
response = http.get("/"+url)
open(file_name, "wb") { |file| file.write(response.body) }
}
file_name
end
def make_web_friendly(file)
# File.join doesn't work for unreal pathes - create by simple concatenation
"/assets/" + File.basename(File.dirname(file)) + "/" + File.basename(file)
end
def get_strip_to_show(file)
if file
path = File.dirname(file)
ext = File.extname(file)
date = Date.strptime(File.basename(file, ext), DATE_FORMAT)
begin
f = path + '/' + (date - 1).strftime(DATE_FORMAT) + ext
date -= 1
end until File.exists?(f)
return f
end
f = Dir[STRIP_DIR+"/*"].sort!.reverse!.first
return download_strip(get_strip_url) if not f
f
end
end
# initialize and show first image
@DD = DailyDilbert.new()
@DD.currentStrip = @DD.get_strip_to_show(@DD.currentStrip)
send_event('daily_dilbert', image: @DD.make_web_friendly(@DD.currentStrip))
# strip download job
SCHEDULER.cron '0 7 * * *' do |job|
url = @DD.get_strip_url
@DD.currentStrip = @DD.download_strip(url)
if not File.exists?(@DD.currentStrip)
warn "Dilbert strip download failed from url #{url} to file #{@DD.currentStrip}"
else
puts DateTime.now.to_s+" Working with #{@DD.currentStrip}, web friendly "+@DD.make_web_friendly(@DD.currentStrip)
send_event('daily_dilbert', image: @DD.make_web_friendly(@DD.currentStrip))
end
end
# strip loop job
SCHEDULER.every '30m', :first_at => Chronic.parse('today 11:00') do |job|
@DD.currentStrip = @DD.get_strip_to_show(@DD.currentStrip)
puts DateTime.now.to_s+" Working with #{@DD.currentStrip}, web friendly "+@DD.make_web_friendly(@DD.currentStrip)
send_event('daily_dilbert', image: @DD.make_web_friendly(@DD.currentStrip))
job.unschedule if Time.now.hour == 6
end
@howardsternisbatman

This comment has been minimized.

howardsternisbatman commented Feb 2, 2015

great widget!

All working great for a number of months now suddenly this

scheduler caught exception:
undefined method []' for nil:NilClass /home/administrator/manchvegas/jobs/daily_dilbert.rb:14:inget_strip_url'
/home/administrator/manchvegas/jobs/daily_dilbert.rb:33:in block in <top (required)>' /var/lib/gems/1.9.1/gems/rufus-scheduler-2.0.24/lib/rufus/sc/jobs.rb:230:incall'
/var/lib/gems/1.9.1/gems/rufus-scheduler-2.0.24/lib/rufus/sc/jobs.rb:230:in trigger_block' /var/lib/gems/1.9.1/gems/rufus-scheduler-2.0.24/lib/rufus/sc/jobs.rb:204:inblock in trigger'
/var/lib/gems/1.9.1/gems/rufus-scheduler-2.0.24/lib/rufus/sc/scheduler.rb:430:in call' /var/lib/gems/1.9.1/gems/rufus-scheduler-2.0.24/lib/rufus/sc/scheduler.rb:430:inblock in trigger_job'

Any ideas?

@JaiDoubleU

This comment has been minimized.

JaiDoubleU commented Feb 3, 2015

The cause is due to the fact that the Dilbert folks restructured their website. The expected format of the page differs significantly from what's there now

@erdeszt

This comment has been minimized.

erdeszt commented Feb 4, 2015

I've updated the script it works for me now: https://gist.github.com/erdeszt/2456979481db4cb8eb00

@Brunas

This comment has been minimized.

Owner

Brunas commented Mar 31, 2015

Hi all,

Thanks guys for comments. I have missed website change myself. The description and all the widget is updated. Have fun!

@fonglh

This comment has been minimized.

fonglh commented Aug 13, 2015

@DD.currentStrip = @DD.get_strip_to_show(@DD.currentStrip)
this line doesn't work when there are no images in the folder, such as when using the job for the first time.

@Brunas

This comment has been minimized.

Owner

Brunas commented Sep 7, 2015

fonglh,

Thanks for your comment. You are right. This will fail if there are no strips downloaded yet. Fixed that by downloading strip in get_strip_to_show if there are no files.

@derwin12

This comment has been minimized.

derwin12 commented Sep 11, 2015

Chronic gem is causing me grief :-(
did gem install chronic .. says its there but for some reason dashing doesnt see it.

@brockklein

This comment has been minimized.

brockklein commented Sep 12, 2015

Don't forget to bundle after installing. That got me past the errors from chronic. Still not getting an image tho.

@shuaiscott

This comment has been minimized.

shuaiscott commented Dec 18, 2015

@brockklein Make sure you add " require 'chronic' " to your Gemfile and bundle again. That worked for me!

@sumdog

This comment has been minimized.

sumdog commented Mar 1, 2016

I see the gif for the daily image in assets/images/dilbert, but it doesn't display the image. Instead I get some weird template dump:

["str", [Tilt::StringTemplate]]["erb", [Tilt::ErubisTemplate, Tilt::ERBTemplate]]["rhtml", [Tilt::ErubisTemplate, Tilt::ERBTemplate]]["erubis", [Tilt::ErubisTemplate]]["etn", [Tilt::EtanniTemplate]]["etanni", [Tilt::EtanniTemplate]]["haml", [Tilt::HamlTemplate]]["mab", [Tilt::MarkabyTemplate]]["liquid", [Tilt::LiquidTemplate]]["radius", [Tilt::RadiusTemplate]]["markdown", [Tilt::RedcarpetTemplate, Tilt::RedcarpetTemplate::Redcarpet2, Tilt::RedcarpetTemplate::Redcarpet1, Tilt::RDiscountTemplate, Tilt::BlueClothTemplate, Tilt::KramdownTemplate, Tilt::MarukuTemplate]]["mkd", [Tilt::RedcarpetTemplate, Tilt::RedcarpetTemplate::Redcarpet2, Tilt::RedcarpetTemplate::Redcarpet1, Tilt::RDiscountTemplate, Tilt::BlueClothTemplate, Tilt::KramdownTemplate, Tilt::MarukuTemplate]]["md", [Tilt::RedcarpetTemplate, Tilt::RedcarpetTemplate::Redcarpet2, Tilt::RedcarpetTemplate::Redcarpet1, Tilt::RDiscountTemplate, Tilt::BlueClothTemplate, Tilt::KramdownTemplate, Tilt::MarukuTemplate]]["textile", [Tilt::RedClothTemplate]]["rdoc", [Tilt::RDocTemplate]]["wiki", [Tilt::WikiClothTemplate, Tilt::CreoleTemplate]]["creole", [Tilt::CreoleTemplate]]["mediawiki", [Tilt::WikiClothTemplate]]["mw", [Tilt::WikiClothTemplate]]["ad", [Tilt::AsciidoctorTemplate]]["adoc", [Tilt::AsciidoctorTemplate]]["asciidoc", [Tilt::AsciidoctorTemplate]]["html", [Tilt::PlainTemplate]]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment