Is "rvenv" a good alternative?
taylor price

No title available

⁂
Cosimo Galluzzi

Discoholic 🪩
todays bird
I'd rather be in outer space 🛸
macklin celebrini has autism
Lint Roller? I Barely Know Her
PUT YOUR BEARD IN MY MOUTH
Sweet Seals For You, Always

❣ Chile in a Photography ❣
will byers stan first human second
RMH
trying on a metaphor

Origami Around
KIROKAZE
2025 on Tumblr: Trends That Defined the Year
Monterey Bay Aquarium
Mike Driver
seen from United States

seen from India

seen from United Kingdom
seen from Malaysia
seen from Lithuania

seen from Brazil
seen from Türkiye

seen from Canada

seen from United Kingdom

seen from Brazil
seen from Egypt

seen from Italy
seen from United States

seen from Malaysia

seen from Türkiye
seen from Netherlands

seen from United States
seen from United States
seen from Türkiye
seen from Türkiye
@rollingonrails-blog
Is "rvenv" a good alternative?
Relationship Types
Allows us to work with the data between our models and tables in an object oriented way.
Relational Database Association:
One-to-One (not used often)
has\_one/belongs\_to
Note to remove the association you can assign nil to it
And to remove the associated record from the database .destroy
One-to-Many (used most often)
has\_many/belongs\_to
belong\_to is where the foreign key goes
Defined Operations:
subject.pages << page #append operator, since pages is a collection of objects
subject.pages = [page, page, page] #you can use equal operator, but you need to provide an array of values
subject.pages.delete(page) #removes the relationship, but does not delete the associated record
subject.pages.destroy(page) #removes the relationship and deletes the associated record
subject.pages.clear #removes the relationships, but not the records
subject.pages.empty?
subject.pages.size
Many-to-Many
has\_many and belongs\_to/has\_many and belongs\_to = has\_and\_belongs\_to\_many
utilizes a joined table (WITH NO ID: , :id => false in it's migration)
Join Table Naming Convention
both table names
alphabetical order
E.g.: BlogPost - Category => BlogPost_Category
Many-to-Many (Rich Joins)
has a Joined table with extra rows
requires ID
Use a descriptive name (no following many-to-many Rails conventions)
require a model (rail generate model [YourModelName])
requires an id for the model
remember to add foreign keys to tables that you want to join
add an index on the combined foreign keys
has\_many/has\_many = belong\_to + belongs\_to
has\_many on the tables to be joined
belongs\_to + belongs\_to on the connecting table (remember, belong\_to goes where the foreign key is)
Note: you can have a different name for the relationship field in your model file, if you specify the way to find the original, E.g.: belongs_to: editor :class_name => "AdminUser", :foreign_key => "admin_user_id". Belongs_to requires a :foreign_key to be specified as well as :class_name.
Note: use .reload on the ActiveRelation object to update it from the db.
Traversing A Rich Join
Allows "reaching across" a rich join, treating it like an HABTM join
E.g.
AdminUser has_many :sections, :through => :section_edits
Section has_many :admin_users, :through => :section_edits
_**Note: ** All the differences between Simple Many-to-Many and Rich Many-to-Many is that the later has a fully functional MODEL._
Active Record, ActiveRelation, Models
Active Record vs ActiveRecord vs ActiveRelation
Active Record
a design pattern for relational databases
is cross plattform (implemented in different language)
let's you work with data as objects, not just static rows
simplifies database operations, including select, insert, updates, delete
ActiveRecord
a Ruby library that let's implements principles of Active Record as pattern.
ActiveRelation (Arel)
New in Rails 3
Simplifies the generation of complex SQL queries
used by ActiveRecord for queries and management of relationship
E.g.
ActiveRecord
user = User.new user.first_name = "Mark" user.save # SQL INSERT user.last_name = "Twain" user.save # SQL UPDATE user.delete #SQL DELETE
ActiveReleation
users = User.where(:first_name => "Mark") users = users.order("last_name ASC").limit(3) users = users.include(:books_written)
Rails Console
allows you to interact with your model the way irb let's you interact with Ruby interpreter. $rails console || rails c
loads rails environment into irb
E.g.: from rails console: Subject.new will create a subject object with attributes mimicking table fields.
CREATE / UPDATE / DELETE / FIND Records
Creating Records
Two ways to create new records.
new / save
Instantiate an object
Set values
Save
create
all three steps as a single command
E.g.
# Number 1 (new / save) subject = Subject.new #creates a new record object (not yet committed to the database) subject.name = "Something"
Alternative way to write it is: subject = Subject.new(:name => "First Subject", :position => 1, :visible => true) subject.save #saves it to the database subject.new_record? #check if the record is still not committed to the database
# Number 2 (create) subject = Subject.create(:name => "Second Subject", :position => 2) # this will commit a record to db and create an object that reflects the newly created record
The first method is used more frequently, since it gives us the flexibility to change an object before committing it to the db.
Update Records
Two ways to do so.
save
find record
set values
save
update_attributes
find record
set values
save
E.g.
# Number 1 (find / update / save) subject = Subject.find(1) subject.name = "Updated Name" #note that name is not updated in the db until `subject.save` is executed subject.save # Number 2 (find / update_attr) subject = Subject.find(2) subject.update_attributes(:name => "Revised Subject", :visible => true) #returns true/false based on if the update succeeded or not
Delete Records
Two ways:
find / destroy
find: subject = Subject.find(2) #by ID in the subjects table
destroy: subject.destroy
The object is accessible after the destroy operation, so the info in it can be used for different purposes (e.g. reporting)
find / delete
bypasses some built-in mechanisms
faster, but doesn't leave a copy to work with
FIND Records
By primary key
User.find(3)
Returns an object or an error
Dynamic finders
find_by_[database field]: User.find_by_first_name("Tyson")
Returns an object or a nil
Find all method
User.all
Returns an array of objects
First/Last method
User.first or User.last
Returns object or nil
Note: all the methods above make a call to the db Immediately
ActiveRelation (Query Methods)
Note: you can use .to_sql method on the AcriveRelation object to output the SQL that was generated.
Note: the where method returns an array, empty array, if no records were matched.
Note: .scoped method is used to instantiate an empty ActiveRelation object and with no additional constrains will match all records in the database. E.g.: User.scoped
Conditions (what conditions data has to meet in order to satisfy the request)
Old Query Methods (depricated in Rails 3.1 and removed in Rails 3.2)
User.find(:first_name, :conditions => ["first_name = ? AND email = '[email protected]'", "Ali"]
User.find(:all, :conditions => {:first_name => 'Bob'})
New (ActiveRelation) Query Methods
where(conditions)
Returns an ActiveRelation object, which can be chained
Name.where(:first_name => 'Ali').order("email ASC")
does not execute a database call immediately
condition can be of three different types:
String "first_name = 'Ali' AND last_name = 'Muhammad'
Flexible, raw SQL
susceptible to SQL injections
Array ["first_name = ? AND last_name = 'Muhammad']
Flexible, escaped SQL
Safe from SQL injections
Hash {:first_name => "Ali", :last_name => "Muhammad"}
Simple, escaped SQL
Safe from SQL injections
Only supports equality, range and subject checking
Order, Limit, Offset
Old Query Methods:
User.find(:all, :order => "email ASC", :limit => 20, :offset => 40)
New (ActiveRelation)
order(sql_fragment)
limit(integer)
offset(integer) #skip over a certain number of records
E.g.: 1) order: user.order("[user.]email ASC, [user.]last_name DESC") 2) limit: user.limit(1) 3) offset: user.offset(1).limit(1)
Named Scopes
Let's you store queries in the model.
You call them same as regular ActiveRecord methods
Can accept parameters
Note: prior Rails 3.0 the method was called named_scope, now it is simply called scope.
E.g.:
in a model class do the following:
scope :klichko where({:first_name => 'Klichko'}) #where ":klichko" is a named scope name
with the parameter:
scope :search, lambda {|query| where(["name LIKE ?", "%#{query}%"])}
Starting Out with Rails
Using the tutorial from lynda.com: Ruby on Rails 3 Essential Training.
Ruby, RubyGems, Rails
Essential commands:
$ruby -v
$ruby -e [ruby_command] #command line interpreter
$which [command] #which command is used, based on the $PATH
Gem - a package manager for ruby: Website
$sudo gem update --system #updates gem utility to the current version
Note: use sudo every time you install/update gems, to make sure that they go into the top level repository.
Rails is not a single gem, it depends an some other ones, like: actionmailer, actionpack, activerecord and so forth.
Gem takes care of all dependencies automatically.
$sudo gem install rails #installs latest rails and all of it's dependencies.
Note: problems that you might encounter: "File not found: lib".
Rails is a gem (that is in itself a set of libraries) and also a small unix program to interface with the installed gem.
$which rails is not going to show you where the rails gem is located, contrary it's going to show where the rails command (unix program) is located.
MySQL
Install latest version from http://dev.mysql.com
Change the root password:
login as root: $mysql -u root
run the following mysql commands: SET PASSWORD FOR root@localhost=PASSWORD('secretpassword'); FLUSH PRIVILEGES;
Create new user to use for the project:
Creates new user GRANT ALL PRIVILEGES ON some_db.* to 'username'@'localhost' IDENTIFIED BY 'user_password';
Verify that the privileges were granted: SHOW GRANTS FOR 'username'@'localhost';
Web Servers
Apache 1 or 2 (with Passenger / mod_rails)
Nginx ("Engine X")
Lighttpd ("Lighty")
Mongrel
WEBrick (ships with Rails)
Databases
Rake
Rake is a simple Ruby helper/builder program; it is a Ruby implementation of Unix Make.
rake db:shema:dump
db:schema - namespace
dump - task
Rake works based on Rakefile (in your project root). You can write your own tasks for it. To see the task that are available to us you can type: rake -T
Note: we can pass variables into rake, e.g.: rake db:schema:dump RAILS_ENV=production #setting RAILS_ENV to production for dump to use.
Migration
Migration is simply a set of database instructions, written in Ruby. Allows us to "migrate" the database from one state to another.
Contains both instructions for "Moving Up" & "Moving Down", e.g.:
create a table / add a column drop column / drop table
Why use Migration:
keeps database schema with application code
is executable and repeatable
allows sharing schema changes
helps with versioning
allows writing Ruby instead of SQL
Has access to your Rails application code
Note: It's not all perfect, but it helps a lot.
Controllers, Views, and Dynamic Content
Controllers
Controller's main function is to control things. Two main parts of it:
The flow of the application
Gather data that it needs (from model and such)
All the View does is formats the things for the output. In order to access data that is gathered by the controller instalce variables (object - controller variables) are used. This variables are set in the controller.
Note: There is no way to go back from the View to the Controller to set something up. Everything must be preset in the Controller for the View to use.
Rendering Templates
How does the controller decides which template to use?
Rails checks if there is any Action that is associated with the request. And if not checks if there is a View for it. If so, even without an action being present rails renders the view.
Render Method
Each action of your controller by default will have a render method executed with the defaults implicitly, if nothing else is specified. That means that the view with the action_name.html.erb under the controller's name folder in the views directory will be rendered for you automatically.
There are a variety of ways to customize the behaviour of render. You can render the default view for a Rails template, or a specific template, or a file, or inline code, or nothing at all. You can render text, JSON, or XML. You can specify the content type or HTTP status of the rendered response as well.
Her are multiple ways to render a view:
render(:action => 'hello')
render(:template => 'demo/hello')
render('demo/hello')
render('hello')
It might be a little confusing, but render(:action => 'hello') doesn't actually calls hello action, what it does is it renders a default template for the hello action, without executing the action itself.
So it will be an equivalent for all the other render examples in the above list.
The last two were added in Rails 3 and are now considered a best practice to use.
More on Render (Rails docs)
Redirect
Redirect is part of the http protocol itself. What Rails does when you are use it's redirect_to method is it send a request back to the browser with the HTTP status code: HTTP/1.1 302 Found and send a Location that it wants the request to be send to, e.g.: Location: http://localhost:3000/demo/hello. So the browser initiates a new request to the new location (all of the processing from the action before the redirect_to was called is lost.)
View Templates
Dynamic Templates with embedded Ruby code (ERb).
hello.html.erb Template name: hello Process with: ERb Output format: HTML
You Embed Ruby code with special tags: <% code %> and <%= code %>. To output Ruby variable you use #{variable_name} inside a double quoted string. E.g.:
<% name = "Alexander" %> <%= "My name is #{name}" %>
Note: you can't use puts and gets in the ERb, those output to the console and not to the generated html. Instead you use <%= %>.
Instance Variables
This are used to pass the data pulled together by the controller in the corresponding view.
Instance variables are variables of an instance of a class (object) and since a Rails controller is simply a class, instance variables are instances of the controller.
Instance variables are marked with an @ sign, e.g.: @instance_variable_name.
Link_to Method
In Rails templates you can use regular <a href="demo/action">Link</a> html links. However it is much more common to use Rails method link_to for that. E.g.: <%= link_to(text, target) %>
Text is the text to be displayed as a link. And target is where the url is going. You can specify the regular "controller/action" as target, but note that it can take Ruby hashes as well.
The syntax to do that is: {:controller => 'demo', :action => 'index'}. You can simply pass the action part, if the url is within the same controller.
The cool thing about this is that routes file is being used to form your url, same way as for the requests coming in.
Additional URL Parameters
When we need to pass additional url parameters like in: http://localhost:3000/demo/hello/3?page=3&name=kevin, we can simply use the same hash notation as we can use with link_to. Everything after the :action will be treated as parameters, e.g.: {:controller => 'demo', :action => 'hello', :id => 1, :page => 3, :name => 'kevin'}.
Note: that since ID is set to have a different meaning in our routes file (match ':controller(/:action(/:id(.:format)))'), the way the it will be appended to the url is different (/#{id} instead if /?id=#{id}).
Another point to note here is that all the url parameters (GET) and POST parameters are send to the system as strings, so in order to do any manipulation with them as integers, you would ned to cast them to such (.to_i).
All the parameters (including controller and action names) are accessible in the Rails/Ruby code using the special params hash.
You can simply access the values of it by passing either a name of the parameter you are looking for as a symbol or a string, e.g.: params[:id] or params['id'].
Note: you can view the content of the params (same as of any other hash, array or other Ruby constract) by calling inspect() method on it, e.g.: params.inspect().
Rails Basics (MVC, Controllers, Views and Routes)
from terminal go to the place where you want your project to be and type:
$rails new [name_of_the_application] -d mysql
Note: -d mysql for preconfiguring with MySQL. Without it it will default to SQLLite.
Rails generates all the necessary files for us.
Before seeing the results on through the web server we will need to launch a web server. We can use the one that is bundled with the rails, called WebBrick.
$rails server (or) $rails s
The server is going to start up and use port 3000 by default. You can see your content @
localhost:3000 (or) 127.0.0.1:3000
MVC Architecture
We are going to be looking at the first three components of it: Browser->Controller->View
Use rails command to generate the controller. From the root of your project execute the following command:
$rails generate controller
This will bring out a help page about the controller and how to generate one
$rails generate controller demo index
Will create a controller called demo and a view that is going to be associated with it called demo.
This will output all the files that were created for you.
Note: Method inside a controller is called an action. It is still a method, but we call it an action.
In the demo controller file, inside your project ([app_name]/app/controllers/demo_controller.rb) there is a method (action) called index. There is also a view with the same file name as an action in the views directory under the folder name with the name of the controller - "demo" ([app_name]/app/views/demo/index.html.erb).
Files Structure of Rails Application
app | |-controllers |-helpers (helper code used by controllers, views and models) |-models |-views config | |-application.rb |-boot.rb |-database.rb |-environment.rb |-locales (localization files for different language) |-routes.rb (how different urls get send to the different parts of the application) config.ru (leave it for now) db (db migration code) doc (documentation for our app, todo lists and such) Gemfile (for 3rd party code, called gems) lib (for 3rd party libraries) log public (files that do not need to be processed by the framework) | |-404.html |-422.html |-500.html |-favicon.ico |-images |-index.html |-javascript |-robots.txt |-stylesheets Rakefile (leave it, used by Rails) README (brief description of your application) script (scripts used by Rails, rails command is in it right now) test (for unit tests) temp (for Rails to put temporary files to) vendor | |-plugins (for 3rd party plugins)
Second take on Rails MVC
First thing the Web Server does is checks in the public directory if the file is there that exactly matches the request from the browser, without accessing the framework.
If the file is not found, the request is going to go to the Rails framework and check the Routing to determine which controller and action to use based on the request URL.
The result is the same - an html page.
Note: the public directory is in the way of the request. So if the file name which matches the request is in that directory it's content is going to be return to the browser, even though we might have meant to execute a controller action instead.
Second Note: the web server is setup the way that ".html" is the default file extension, so request to index and index.html will be treated identically and will return the content of the index.html back to the browser.
Routes
In your routes.rb file in the config folder you will see a generated simple route and a bunch of examples on how to write complex routes.
get "demo/index" is equivalent to match "demo/index", :to => "demo#index"
It's just a one to one match.
Default Route
match ':controller(/:action(/:id(.:format)))'
":" indicates that it is a Ruby symbol. This will route all the url request to the actions under the controllers that they belong to. And will pass the id of the db record to it if needed.
E.g: http://yourapp.com/activity/show/53 will be routed to the action called "show" in the "activity" controller and will pass 53 as a parameter.
Root Route
root :to => "demo#index"
Is used for the routing requests to the root of the application.
E.g.: http://yourapp.com/ will be routed to index action of the demo controller.
Problems during setup (Rails 3.0 MySQL2)
While running $rails server to start rails server (WEBrick) I got what looks to be a soft warning:
WARNING: This version of mysql2 (0.3.2) doesn't ship with the ActiveRecord adapter bundled anymore as it's now part of Rails 3.1 WARNING: Please use the 0.2.x releases if you plan on using it in Rails <= 3.0.x
Which basically breaks the data connection to MySQL database as a whole.
While there seems to be a lot of information on the web on how to deal with this "Warning" message, e.g. MySQL2 gem GitHub page, StackOverflow. I didn't quiet get it from their description. What is a Gemfile and what is the version of the mysql2 gem that I'm suppose to look for, 0.2.x is not really desciptive or should I just pick a random number instead of x? =)
Here is what I did
Looks like you need to somehow make gem install mysql2 of any version of 0.2.x. I didn't find a way to specify the gem version number with the gem command. Though I found Gemfile in the project root folder, which looks to be a configuration file for the gems that are used by the application. In it you will see the following line:
gem 'mysql2'
Which just says to use whatever version of mysql2 gem that is installed on the system. Update it to:
gem 'mysql2', '0.2.7'
Which specifically says to use mysql2 version 0.2.7 (the latest of the 0.2.x series).
Now what we need to do is somehow install it on the system. And looks like command (run inside your project directory):
$bundle install
does just that. It seems to compare the specifications in the Gemfile to what is available on the system and downloads all the gems that are missing.
There you have it. Problem solved. =)