mirror of
https://github.com/wahyd4/emoji-cheat-sheet.com.git
synced 2026-08-09 05:07:04 +10:00
Added pre-deploy sprite generator
Sprite generator now with less suck
This commit is contained in:
@@ -2,3 +2,4 @@ source :rubygems
|
||||
gem 'fog'
|
||||
gem 'mime-types'
|
||||
gem 'rake'
|
||||
gem 'nokogiri'
|
||||
|
||||
@@ -29,4 +29,5 @@ PLATFORMS
|
||||
DEPENDENCIES
|
||||
fog
|
||||
mime-types
|
||||
nokogiri
|
||||
rake
|
||||
|
||||
@@ -1,125 +1,11 @@
|
||||
require 'rubygems'
|
||||
require 'bundler'
|
||||
Bundler.require
|
||||
|
||||
require 'digest/sha1'
|
||||
require_relative 'lib/simple_s3_deploy'
|
||||
require_relative 'lib/emoji_optimizer'
|
||||
|
||||
task :deploy do
|
||||
SimpleS3Deploy.deploy('public')
|
||||
end
|
||||
|
||||
|
||||
module SimpleS3Deploy
|
||||
|
||||
def self.deploy(site_path)
|
||||
Site.new(site_path).deploy
|
||||
EmojiOptimizer.new(:size => 22, :padding => 5).optimize! do
|
||||
SimpleS3Deploy.deploy('public')
|
||||
end
|
||||
|
||||
class Site
|
||||
attr_accessor :path
|
||||
attr_accessor :tmp_files
|
||||
|
||||
def initialize(path)
|
||||
@path = path
|
||||
@tmp_files = []
|
||||
end
|
||||
|
||||
def deploy
|
||||
puts " ** Deploying #{path} to #{bucket.key}"
|
||||
puts " ========================================================"
|
||||
puts " ** Deleting existing remote files"
|
||||
clear_bucket
|
||||
puts " ** Uploading files"
|
||||
files.each do |file|
|
||||
if !File.directory?(file.path)
|
||||
remote_file_name = file_base_path(file.path)
|
||||
puts " Uploading #{remote_file_name} .."
|
||||
bucket.files.create(
|
||||
key: remote_file_name,
|
||||
body: file.is_minifyable? ? open(minify(file.path)) : open(file.path),
|
||||
public: true,
|
||||
content_type: file.mime_type,
|
||||
cache_control: 'max-age=604800, public' )
|
||||
end
|
||||
end
|
||||
if tmp_files.any?
|
||||
puts " ** Cleaning up tmp files"
|
||||
cleanup
|
||||
end
|
||||
puts "\n ** Done"
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def clear_bucket
|
||||
bucket.files.each do |f|
|
||||
puts " Deleting #{f.key}"
|
||||
f.destroy
|
||||
end
|
||||
end
|
||||
|
||||
def cleanup
|
||||
tmp_files.each do |file|
|
||||
puts " Deleting #{file}"
|
||||
File.unlink(file)
|
||||
end
|
||||
end
|
||||
|
||||
def files
|
||||
@files ||= Dir.glob("#{path}/**/*").map { |f| SiteFile.new(f) }
|
||||
end
|
||||
|
||||
def file_base_path(file)
|
||||
file.gsub("#{path}/", "")
|
||||
end
|
||||
|
||||
def minify(file_path)
|
||||
"#{file_path}-tmp".tap do |tmp_file_name|
|
||||
`yuicompressor -o #{tmp_file_name} #{file_path}`
|
||||
tmp_files << tmp_file_name
|
||||
end
|
||||
end
|
||||
|
||||
def config
|
||||
@config ||= YAML.load_file('config.yaml')
|
||||
end
|
||||
|
||||
def s3
|
||||
@s3 ||= Fog::Storage.new({
|
||||
provider: 'AWS',
|
||||
aws_secret_access_key: config['s3']['secret_access_key'],
|
||||
aws_access_key_id: config['s3']['access_key_id'] })
|
||||
end
|
||||
|
||||
def bucket
|
||||
@bucket ||= s3.directories.get(config['s3']['bucket'])
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
class SiteFile
|
||||
attr_accessor :path
|
||||
|
||||
def initialize(_path)
|
||||
@path = _path
|
||||
end
|
||||
|
||||
def is_minifyable?
|
||||
is_css_file? or is_js_file?
|
||||
end
|
||||
|
||||
def is_css_file?
|
||||
path.end_with?('.css')
|
||||
end
|
||||
|
||||
def is_js_file?
|
||||
path.end_with?('.js')
|
||||
end
|
||||
|
||||
def mime_type
|
||||
MIME::Types.type_for(path)[0].to_s
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
@@ -0,0 +1,128 @@
|
||||
require 'digest/md5'
|
||||
require 'tmpdir'
|
||||
|
||||
class EmojiOptimizer
|
||||
|
||||
def initialize(options = {})
|
||||
@size = options.delete(:size) { 22 }
|
||||
@padding = options.delete(:padding) { 5 }
|
||||
@source = Source.new('public/index.html')
|
||||
end
|
||||
|
||||
def optimize!(&block)
|
||||
puts " ** Preparing for optimization"
|
||||
prepare
|
||||
|
||||
puts " ** Generating emoji sprite image"
|
||||
if @source.create_sprite(@size, @padding, sprite_path)
|
||||
puts " ** Generating css and updating markup"
|
||||
generate_and_save
|
||||
else
|
||||
puts " ** Could not generate emoji sprite =("
|
||||
end
|
||||
|
||||
yield
|
||||
|
||||
ensure
|
||||
puts " ** Cleaning up after optimization"
|
||||
cleanup
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def prepare
|
||||
FileUtils.cp 'public/index.html', File.join(tmp_dir, 'index.html')
|
||||
FileUtils.cp 'public/emoji.css', File.join(tmp_dir, 'emoji.css')
|
||||
end
|
||||
|
||||
def generate_and_save
|
||||
update_source_markup
|
||||
|
||||
File.open('public/emoji.css', 'a') { |f| f.puts css_rules.join("\n") }
|
||||
File.open('public/index.html','w') { |f| f.write @source.to_html }
|
||||
FileUtils.mv sprite_path, "public/graphics/#{digest_name}"
|
||||
end
|
||||
|
||||
def cleanup
|
||||
FileUtils.mv File.join(tmp_dir, 'index.html'), 'public/index.html'
|
||||
FileUtils.mv File.join(tmp_dir, 'emoji.css'), 'public/emoji.css'
|
||||
FileUtils.rm_f "public/graphics/#{@digest_name}"
|
||||
end
|
||||
|
||||
def css_rules
|
||||
[].tap do |rules|
|
||||
rules << %Q{
|
||||
.emoji {
|
||||
display:inline-block;
|
||||
width:#{@size}px;
|
||||
height:#{@size}px;
|
||||
background:transparent url(/graphics/#{digest_name}) 0 0 no-repeat;
|
||||
}
|
||||
}
|
||||
@source.emojis.size.times do |index|
|
||||
rules << css_sprite_mapping(index)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def update_source_markup
|
||||
@source.emojis.each_with_index do |img, index|
|
||||
img.replace @source.create_element('span', {
|
||||
'id' => "e_#{index+1}",
|
||||
'class' => 'emoji',
|
||||
'data-src' => img['src']
|
||||
})
|
||||
end
|
||||
end
|
||||
|
||||
def css_sprite_mapping(index)
|
||||
offset = ((@size + @padding * 2) * index) + @padding
|
||||
"#e_#{index+1} { background-position:-#{offset}px 0; }"
|
||||
end
|
||||
|
||||
def sprite_path
|
||||
@sprite_path ||= File.join(tmp_dir, 'sprite.png')
|
||||
end
|
||||
|
||||
def digest_name
|
||||
@digest_name ||= "sprite_#{Digest::MD5.hexdigest(File.read(sprite_path))}.png"
|
||||
end
|
||||
|
||||
def tmp_dir
|
||||
@tmp_dir ||= Dir.mktmpdir 'emoji-optimization'
|
||||
end
|
||||
|
||||
class Source
|
||||
|
||||
def initialize(file)
|
||||
@file = file
|
||||
end
|
||||
|
||||
def emojis
|
||||
@emojis ||= doc.css('#content img').find_all { |img| img['src'] =~ /emojis/ }
|
||||
end
|
||||
|
||||
def emoji_paths
|
||||
@emoji_paths ||= emojis.map { |img| File.join('public', img['src']) }
|
||||
end
|
||||
|
||||
def create_sprite(size, padding, path)
|
||||
system "montage #{emoji_paths.join(' ')} -tile x1 -geometry #{size}x#{size}+#{padding} -background transparent #{path}"
|
||||
end
|
||||
|
||||
def create_element(*args)
|
||||
doc.create_element *args
|
||||
end
|
||||
|
||||
def to_html
|
||||
doc.to_html
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def doc
|
||||
@doc ||= Nokogiri::HTML(File.open(@file))
|
||||
end
|
||||
|
||||
end
|
||||
end
|
||||
@@ -0,0 +1,114 @@
|
||||
module SimpleS3Deploy
|
||||
|
||||
def self.deploy(site_path)
|
||||
Site.new(site_path).deploy
|
||||
end
|
||||
|
||||
class Site
|
||||
attr_accessor :path
|
||||
attr_accessor :tmp_files
|
||||
|
||||
def initialize(path)
|
||||
@path = path
|
||||
@tmp_files = []
|
||||
end
|
||||
|
||||
def deploy
|
||||
puts " ** Deploying #{path} to #{bucket.key}"
|
||||
puts " ========================================================"
|
||||
puts " ** Deleting existing remote files"
|
||||
clear_bucket
|
||||
puts " ** Uploading files"
|
||||
files.each do |file|
|
||||
if !File.directory?(file.path)
|
||||
remote_file_name = file_base_path(file.path)
|
||||
puts " Uploading #{remote_file_name} .."
|
||||
bucket.files.create(
|
||||
key: remote_file_name,
|
||||
body: file.is_minifyable? ? open(minify(file.path)) : open(file.path),
|
||||
public: true,
|
||||
content_type: file.mime_type,
|
||||
cache_control: 'max-age=604800, public' )
|
||||
end
|
||||
end
|
||||
if tmp_files.any?
|
||||
puts " ** Cleaning up tmp files"
|
||||
cleanup
|
||||
end
|
||||
puts "\n ** Done"
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def clear_bucket
|
||||
bucket.files.each do |f|
|
||||
puts " Deleting #{f.key}"
|
||||
f.destroy
|
||||
end
|
||||
end
|
||||
|
||||
def cleanup
|
||||
tmp_files.each do |file|
|
||||
puts " Deleting #{file}"
|
||||
File.unlink(file)
|
||||
end
|
||||
end
|
||||
|
||||
def files
|
||||
@files ||= Dir.glob("#{path}/**/*").map { |f| SiteFile.new(f) }
|
||||
end
|
||||
|
||||
def file_base_path(file)
|
||||
file.gsub("#{path}/", "")
|
||||
end
|
||||
|
||||
def minify(file_path)
|
||||
"#{file_path}-tmp".tap do |tmp_file_name|
|
||||
`yuicompressor -o #{tmp_file_name} #{file_path}`
|
||||
tmp_files << tmp_file_name
|
||||
end
|
||||
end
|
||||
|
||||
def config
|
||||
@config ||= YAML.load_file('config.yaml')
|
||||
end
|
||||
|
||||
def s3
|
||||
@s3 ||= Fog::Storage.new({
|
||||
provider: 'AWS',
|
||||
aws_secret_access_key: config['s3']['secret_access_key'],
|
||||
aws_access_key_id: config['s3']['access_key_id'] })
|
||||
end
|
||||
|
||||
def bucket
|
||||
@bucket ||= s3.directories.get(config['s3']['bucket'])
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
class SiteFile
|
||||
attr_accessor :path
|
||||
|
||||
def initialize(_path)
|
||||
@path = _path
|
||||
end
|
||||
|
||||
def is_minifyable?
|
||||
is_css_file? or is_js_file?
|
||||
end
|
||||
|
||||
def is_css_file?
|
||||
path.end_with?('.css')
|
||||
end
|
||||
|
||||
def is_js_file?
|
||||
path.end_with?('.js')
|
||||
end
|
||||
|
||||
def mime_type
|
||||
MIME::Types.type_for(path)[0].to_s
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
end
|
||||
Reference in New Issue
Block a user