Rails: Including HTML in your i18n locales
TL;DR
Append your locale keys with _html to have them marked as
html_safeand translate them with= t('.text_html').
When you're localizing a Rails application, sometimes there is this urge to include a little HTML. Be it some localized link, or a set of <em> tags, you'd like to have it included in the locale file. Example:
# Locale file
en:
page:
text: 'Please visit our <a href="https://www.corporate.com/en">corporate website</a> to learn more about <em>the corporation</em>.'
# HAML
= t('.text')
# D...
Capistrano task to tail remote application logs of multiple servers
When your application is running on a multi-server setup, application logs are stored per server (unless you choose a centralized logging solution).
Here is a Capistrano task that connects to all servers and prints logs to your terminal like this:
$ cap production app:logs
00:00 app:logs
01 tail -n0 -F /var/www/your-application/shared/log/production.log | while read line; do echo "$(hostname): $line"; done
01 app01-prod: Started GET "/sign_in" for 1.2.3.4 at 2018-04-26 11:28:19 +0200
01 app01-prod: Proc...
Unpoly: Loading large libraries on-demand
When your JavaScript bundle is so massive that you cannot load it all up front, I would recommend to load large libraries from the compilers that need it.
Compilers are also a good place to track whether the library has been loaded before. Note that including same <script> tag more than once will cause the browser to fetch and execute the script more than once. This can lead to memory leaks or cause duplicate event handlers being registered.
In our work we mostly load all JavaScript up front, since our bundles are small enough. We recent...
jQuery: How to replace DOM nodes with their contents
You know that you can use jQuery's text() to get an element's contents without any tags.
If you want to remove only some tags, but keep others, use contents() and unwrap(). Here is how.
Consider the following example element.
$container = $('<div><strong>Hello</strong> <em>World</em></div>')
Let's say we want to discard any <em> tags, but keep their contents.
Simply find them, then dive into their child nodes via contents, and use unwrap replace their ...
When you want to format only line breaks, you probably do not want `simple_format`
For outputting a given String in HTML, you mostly want to replace line breaks with <br> or <p> tags.
You can use simple_format, but it has side effects like keeping some HTML.
If you only care about line breaks, you might be better off using a small, specialized helper method:
def format_linebreaks(text)
safe_text = h(text)
paragraphs = split_paragraphs(safe_text).map(&:html_safe)
html = ''.html_safe
paragraphs.each do |paragraph|
html << content_tag(:p, paragraph)
end
html
end
Full di...
Rails: How to provide a public link in a mail
Lets say we have a user with a contract whereas contract is a mounted carrierwave file.
Now we want to send the link to the contract in a mail. For this use case join the root_url with the public contract path in the mailer view:
Plain text email
URI.join(root_url, @user.contract.url)
HTML email
link_to('Show contract', URI.join(root_url, @user.contract.url).to_s)
Note: You need to follow [http://guides.rubyonrails.org/action_mailer_basics.html#g...
Fixing: Gem::Package::PathError: installing into parent path is not allowed
This might be a known issue with Rubygems 2.5.1. This will help:
gem update --system
Generating test images on the fly via JavaScript or Ruby
When you need test images, instead of using services like lorempixel or placehold.it you may generate test images yourself.
Here we build a simple SVG image and wrap it into a data: URI. All browsers support SVG, and you can easily adjust it yourself.
Simply set it as an image's src attribute.
JavaScript
Simple solution in modern JavaScript, e.g. for use in the client's browser:
function svgUri(text) {
let svg = `
<svg wid...
How to resize your boot partition when there is an encrypted partition after it
Boot partitions from installations prior to the 16.04 era are terribly small. When you install updates and encounter errors due to a full /boot partition, consider risizing it.
If you can't do the steps described below, ask someone experienced to help you out.
This has worked 100% so far. 1 out of 1 tries. ;)
Scenario A: There is unassigned space on your physical drive
When there is some unpartitioned space on your drive, increasing the size of /boot is actually very easy (even though the list below is rather long). It only takes a...
Geordi 1.9 released
New features:
geordi delete_dumps [directory]
Recursively search for files ending in *.dump and offer to delete those. When no argument is given, two default directories are searched for dump files: the current working directory and ~/dumps (for dumps created with geordi).
geordi drop_databases
Delete local MySQL/MariaDB and Postgres databases that are not whitelisted.
Authentication is handled via PAM for Postgres and MariaDB, via .my.cnf with fallback to mysql -p for MySQL. Different connection methods can be chosen via ...
Rails: Overriding view templates under certain conditions only
Rails offers a way to prepend (or append) view paths for the current request. This way, you can make the application use different view templates for just that request.
Example
A use case of this is a different set of view templates that should be used under certain circumstances:
class UsersController < ApplicationController
before_action :prepare_views
def index
# ...
end
private
def prepare_views
if <condition>
prepend_view_path Rails.root.join('app', 'views', 'special')
end
end
...
Writing strings as Carrierwave uploads
When you have string contents (e.g. a generated binary stream, or data from a remote source) that you want to store as a file using Carrierwave, here is a simple solution.
While you could write your string to a file and pass that file to Carrierwave, why even bother? You already have your string (or stream).
However, a plain StringIO object will not work for Carrierwave's ActiveRecord integration:
>> Attachment.create!(file: StringIO.new(contents))
TypeError: no implicit conversion of nil into String
This is because Carrierwav...
HTML5: disabled vs. readonly form fields
Form fields can be rendered as noneditable by setting the disabled or the readonly attribute. Be aware of the differences:
disabled fields
- don’t post to the server
- don’t get focus
- are skipped while tab navigation
- available for
button,fieldset,input,select,textarea,command,keygen,optgroup,option
Browser specific behavior:
- IE 11: text inputs that are descendants of a disabled fieldset appear disabled but the user can still interact with them
- Firefox: selecting text in a disabled text field is no...
How to: Restart vnc server for geordi
Trying to open a vnc window with geordi geordi vnc ended up with this error:
> VNC viewer could not be opened:
vncviewer: ConnectToTcpAddr: connect: Connection refused
Check if vncserver 17 (default geordi session) is running:
ps -aux|grep vnc
If you see Xvnc4 :17 then the server is already running. Kill this server if it is already running.
vncserver -kill :17
Als...
Mysql::Error: BLOB/TEXT column can't have a default value
mysql> SELECT @@global.version;
+------------------+
| @@global.version |
+------------------+
| 5.6.30 |
+------------------+
1 row in set (0,00 sec)
MySQL 5.6 Reference Manual says "BLOB and TEXT columns cannot have DEFAULT values".
If you want to run migrations in development here are two variants which might help. If you are not sure about the side effects (e.g. your application is broken when it doesn't set additional default values on application side, too...
Chrome: Making high-resolution website screenshots without add-ons
If you want to make a screenshot of a website that works well in print or on a high-DPI screen (like Apple Retina displays), here is how you can capture a high-resolution screenshot.
You can do this without an addon:
- Open the website
- If you have multiple monitoros:
- Resize the Chrome window so it covers multiple monitors (in Linux you can hold ALT and resize by dragging with the right mouse button)
- Zoom into the page using
CTRL +andCTRL -so it covers most of the window area. Leave a little padding on the left and right so...
XHR is not JSON
When a Rails controller action should handle both HTML and JSON responses, do not use request.xhr? to decide that. Use respond_to.
I've too often seen code like this:
def show
# ...
if request.xhr?
render json: @user.as_json
else
# renders default HTML view
end
end
This is just plain wrong. Web browsers often fetch JSON via XHR, but they (should) also send the correct Accept HTTP header to tell the server the data they expect to receive.
If you say request.xhr? as a means for "wants JSON" you are ...
About-Payments: Platform to compare payment providers
About-Payments is here to help you to accept payments online and
find the best payment service provider for your e-commerce business.
Carrierwave: Deleting files outside of forms
TL;DR Use user.update!(remove_avatar: true) to delete attachments outside of forms. This will have the same behavior as if you were in a form.
As you know, Carrierwave file attachments work by mounting an Uploader class to an attribute of the model. Though the database field holds the file name as string, calling the attribute will always return the uploader, no matter if a file is attached or not. (Side note: use #present? on the uploader to check if the file exists.)
class User < ApplicationRecord
mount :avatar, ...
Form letters with LibreOffice Writer
This is painful. Consider using Microsoft Office or switching careers. If you need to write < 20 letters consider doing it manually.
So you didn't listen and here it comes:
- Ignore the Mail Merge Wizard. It will crash or destroy your document.
- Export your addresses, recipient names, etc. as a
.odsspreadsheet (.xls,.xlsx,.ods). Use any columns that work for you, but be consistent. I like to use one column for the address, one column for the salutation line. - Import the spreadsheet as an address book source: *Tools => Add...
How to use cookies with curl
When making requests using curl, no cookies are sent or stored by default.
However, you can tell curl to re-use cookies received earlier (or forge your own cookies).
There are 2 command line switches you need to use:
-
-cwill write cookies to a given file -
-bwill read cookies from a given file
Example
The remote server sets a "foo" cookie to value "bar". We tell curl to store them to a file at /tmp/cookies using the -c switch.
$ curl -c /tmp/cookies http://httpbin.org/cookies/set?foo=bar
You may look at the file, ...
Rails: Migration helper for inserting records without using models
You should avoid using application models in your migrations. But how else could you create records in a migration?
The most basic way is to write plain SQL, but since INSERT statements are no pleasant write for Rubyists, here is a simple wrapper:
Record creation helper for migrations
The helper method below takes a table name and a hash of attributes, which it inserts into the specified table. Copy it over to your migration and profit!
private
def insert_record(table, **attributes)
attributes.merge!...
How to fix HTML elements being cut off when printing
When you print (or print preview) and elements are cut off (e.g. after 1st page, or "randomly") you should check your CSS rules for these:
-
Is there an element with "
display: inline-block" that surrounds your content? Make sure it has "display: block" for printing.
This primarily affects Firefox and Internet Explorer. Chrome seems to be able to handleinline-blockelements in most cases. -
Does the element itself, or a container, define "
overflow: hidden"? Use "overflow: auto" (or maybe "overflow: visible") instead. -
Is th...
HTML: Making browsers wrap long words
By default, browsers will not wrap text at syllable boundaries. Text is wrapped at word boundaries only.
This card explains some options to make browsers wrap inside a long word like "Donaudampfschifffahrt".
Option 1: hyphens CSS property (preferred)
Modern browsers can hyphenate natively. Use the hyphens CSS property:
hyphens: auto
There is also hyphens: none (disable hyphenations even at ­ entities) and hyphens: manual (hy...