Dynamic categories with docpad - docpad

I have the following posts in my blog :
src/documents/posts/foo.html.md
---
category: cooking
---
src/documents/posts/bar.html.md
---
category: programmation
---
I would like to generate the following routes :
http://example.org/cooking/
http://example.org/programmation/
Where each route would have a collection with only posts in the selected category. The posts would still be in the standard place :
http://example.org/posts/foo.html
http://example.org/posts/bar.html
Bonus point : I would also like to be able to list categories in my layout. Something like :
<% for cat in #getCategories() %>
<%= cat.name %>
<% endfor %>
Is there a plugin already existing which give these kind of functionalities ? If not, what's the best way to starting implementing it ?
I have seen the setFilter method in this answer, but I'm still struggling to find out how to generate new pages after parsing every posts to fetch categories.
If dynamic page generation cannot be achieved (which I could understand, since it would require to parse pages in a specific order), would having a static array in the configuration make it easier ?

Have a look at this related plugin :
https://github.com/docpad/docpad-plugin-related
As far as I know it doesn't generate tags pages automatically for you, but that's a good start.

I was able to do this same thing with a tags plug-in: https://github.com/rantecki/docpad-plugin-tagging
It automagically creates views for each tag you use. Listing the categories is pretty simple as well. Here's what I've got, using a select box:
<select ONCHANGE="location = this.options[this.selectedIndex].value;">
<option value="">Choose</option>
<% for tag, data of #getTagCloud(): %>
<option value="<%= data.url %>">
<%= tag %>
</option>
<% end %>
</select>

Related

Chef - Passing Attributes in an array to a template as multiple lines

In my attributes I am trying to create server admins to be passed to a template. However, because of how the template is read by the linux server, they need to be individual lines in the template for each admin.
How would I make this a reality by just using my attributes, and a template?
In the Template .erb file -
Admins= <%= node['game_server']['game_session']['admin1'] %>
Admins= <%= node['game_server']['game_session']['admin2'] %>
My attributes file lines look like this -
default['game_server']['game_session']['admin1'] = 'admin1'
default['game_server']['game_session']['admin2'] = 'admin2'
I want to make an Array in attributes, and have the template.erb file pull them... Something like this would be nice in an attribute file instead of individual lines defining each admin -
An Example of what I'd like to do (if possible) -
default['game_server']['server_admins'] = {
'admin1': { 'Admins=': 'admin1' },
'admin2': { 'Admins=': 'admin2' },
}
I'm just learning Chef as an Ops person, so sorry for a noob question. I don't know much about programming languages yet.
attributes:
default['game_server']['server_admins'] = ['admin1', 'admin2']
template:
<% node['game_server']['server_admins'].each do |admin| %>
Admins= <%= admin %>
<% end %>

Rails 5 rendering partials and passing data

I'm having trouble getting traction on what the general ways data gets passed around from and is made available to partials.
For example:
I have a controller handing off an instance variable to a template that renders a partial:
static_pages_controller.rb:
def home
#feed_items = current_user.feed
end
home.html.erb:
<%= render 'shared/feed' %>
_feed.html.erb:
<%= render #feed_items %>
Now, inside my User model is an instance method that reaching into the database to get her posts:
user.rb:
def feed
Micropost.where("user_id = ?", id)
end
So somehow because Micropost.where(...) returns a collection of microposts is that how Rails knows to go from _feed.html.erb to another partial where the <li> is defined for how microposts want to be defined?
_micropost.html.erb:
<li id="micropost-<%= micropost.id %>">
<%= link_to adorable_avatar_for(micropost.user, size: 50), micropost.user %>
</li>
And also is it just a convention that because I'm really handling a collection of microposts that Rails knows to give the micropost variable?
Your questions are answered in the Ruby on Rails Guides on Layouts and Rendering. It's worth reading the information on partials that comes before the quoted passages below as well:
Every partial also has a local variable with the same name as the
partial (minus the underscore). You can pass an object in to this
local variable via the :object option:
<%= render partial: "customer", object: #new_customer %>
Within the customer partial, the customer variable will refer to
#new_customer from the parent view. (Earlier the Guide instructs that to specify other options for render(), e.g. object:, you have to explicitly specify partial: and the name of the partial.)
If you have an instance of a model to render into a partial, you can
use a shorthand syntax:
<%= render #customer %>
Assuming that the #customer instance variable contains an instance of
the Customer model, this will use _customer.html.erb to render it and
will pass the local variable customer into the partial which will
refer to the #customer instance variable in the parent view.
3.4.5 Rendering Collections
Partials are very useful in rendering collections. When you pass a
collection to a partial via the :collection option, the partial will
be inserted once for each member in the collection:
index.html.erb:
<h1>Products</h1>
<%= render partial: "product", collection: #products %>
_product.html.erb:
<p>Product Name: <%= product.name %></p>
When a partial is called with a pluralized collection, then the
individual instances of the partial have access to the member of the
collection being rendered via a variable named after the partial. In
this case, the partial is _product, and within the _product partial,
you can refer to product to get the instance that is being rendered.
There is also a shorthand for this. Assuming #products is a collection
of product instances, you can simply write this in the index.html.erb
to produce the same result:
<h1>Products</h1>
<%= render #products %>
Rails determines the name of the partial to use by looking at the
model name in the collection. In fact, you can even create a
heterogeneous collection and render it this way, and Rails will choose
the proper partial for each member of the collection:
index.html.erb:
<h1>Contacts</h1>
<%= render [customer1, employee1, customer2, employee2] %>
customers/_customer.html.erb:
<p>Customer: <%= customer.name %></p>
employees/_employee.html.erb:
<p>Employee: <%= employee.name %></p>
In this case, Rails will use the customer or employee partials as
appropriate for each member of the collection.
In the event that the collection is empty, render will return nil, so
it should be fairly simple to provide alternative content.
<h1>Products</h1>
<%= render(#products) || "There are no products available." %>

Rails 3 each method and Ajax

I'm trying to implement some Ajax in my app. A strange behaviour occurs!
It's a daycare application. When you show a specific daycare of a specific date you can add some children.
Originally a list of the children of the database is generated and when you click on one of them the page reload and a new child appears in the attendance list of the daycare. It's working fine, i just wanna add some ajax to be more userfriendly !
When you click on child to add him to the daycare, a daycare_item is created ( join table, an id of the child and the id of the daycare ).
I make the changes to make it ajax ready:
partial for the list
format.js in the daycare_item controller
remote true on the link.
It works, no more reload! But the list is updated only when you click a second time on the children list ( the last child added doesn't appears yet ). The js transaction works and if you refresh manually the page, the missing child appears.
I tried few things and here are my results:
In my partial there are
<% #daycare.daycare_items.each do |c| %>
<li><%= c.child.firstname ></li>
<% end %>
This produce the "lag" effect with one children who is not showing ( until a full refresh )
But if i put a
<%= #daycare.daycare_items.count %>
the code is update in time !
I see nothing strange in the logs.
I'm asking why the .each method make a difference?
A var was stoping a part of the code to be executed, the var wasn't wrong and doesn't generate an error.
The elements involved:
daycare_items controller
def create
#daycare = Daycare.find(params[:daycare_id]) # for Ajax
#daycare_item = DaycareItem.new(params[:daycare_item])
....
end
the create.js.erb
$('#children-list').html(" <%=j render partial: 'daycares/daycare', locals: { daycare: #daycare } %> ");
the view daycares#show
<div id="children-list">
<%= render #daycare %>
</div>
the partial ( a part of ) _daycare.html.erb
<p>counting test:<%= daycare.daycare_items.count %></p>
# here was something like this <%= #waiting.count %> #waiting is define in the daycare controller but not in the daycare_items controller
<p>
<% daycare.daycare_items.each do |dci| %>
<%= dci.enfant.prenom %>
<% end %>
</p>

Update a Rails 3 partial using AJAX (not a form)

I found a number of questions and answers regarding updating a partial using Ajax after submitting a form. But my question is ?simpler?, I just want to reload a partial every few seconds and load in the new data. This really can't be hard at all, and I remember doing something similar in Rails 2.3 but I can't find the answer anywhere.
Basically, I have a show.html.erb rendering a partial like so:
<div id="latest_post">
<%= render :partial=>'info/latest', :object=>#user, :as=>:user %>
</div>
The partial file located at app/views/info/_latest
<% post = user.posts.last %>
<h1>Last Post</h1>
<p><%= post.content %></p>
I just want the latest_post div to be updated every 30 seconds. Please help!
Well it turns out the answer is a little complicated:
Step 1: Use Javascript's setInterval function along with jQuery's $.get() function to load a page, say /users/1/posts/latest.
setInterval(function(){
$.get("/users/1/posts/latest.js", function(data){
$("latest_post").html(data);
},
"html")
}, 30000);
Step 2: Create a latest.js.erb and put it in your app/views/posts folder.
Contents of latest.js.erb:
<%= render partial: 'posts/latest', object: #user.posts.last, as: :post %>
Step 3: Create the above partial with whatever you'd like (if you don't need a partial, you can just write the entire contents of the div in the latest.js.erb file.)
Step 4: Add a latest method to your PostsController, that defines #user, etc. for the latest.js.erb to use.
Step 5: Add get '/latest' to your routes.rb

Rails forms -- accessing a variable that is not part of the form

I want to make a form for submitting the info needed to create an instance of model X and save it to the database, but I have a slight problem: I know how to add form fields like text areas and what not and then how to make those values accessible when the create method is called, but what if I want to also send make a value that is not part of the form accessible? For example, what if I want to be able to access some text in a <div> of my html document and send that to the create method for model X (so it can be stored in like a content variable or something)? How do I do that?
Short answer is you can't - to send data to the server, it has to be in an form field.
Longer answer - there are ways around this and you have several options - put the text in a textarea and style it to look like an div, or put it in a hidden field when the template is created, or use javascript to copy it into a hidden field ... all depends on what you are trying to do really. Perhaps you could give some more detail?
In your model you want to use attr_accessor
What you can do is use attr_accessor which creates a virtual attribute that you can use in the model but is discarded after that.
For example:
app/models.post.rb
class Post < ActiveRecord::Base
attr_accessor :some_variable
#now you can access 'some_variable' this variable in the model
#try Post.some_variable in the console
end
app/views/posts/_form.html.erb
<div id="form">
<div class="field">
<%= f.label :some_variable %>
<%= f.text_field :some_variable %>
</div>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
</div>

Resources