2009-04-22 11 views
7

Chcę stworzyć CMS jak miejsca, w którym użytkownik rozpoczyna mecz w niektórych stronach generycznych, czyliDynamiczny CMS jak trasach w Ruby on Rails

  • stronę
  • o
  • kontakt
  • etc

a stamtąd można dodawać stron podrzędnych dynamicznie, na przykład

  • stronę
    • artykuły
      • art.1
        • coś
          • coś-else
      • Article2
  • o
  • kontakt
  • itp

Do tego mam zamiar osiągnąć stosując na jakiś własny referential stowarzyszenia jak

class Page < ActiveRecord::Base 
    belongs_to :parent, :class_name => 'Page' 
    has_many :children, :class_name => 'Page' 
end 

Jedną rzeczą, z którą walczę, jest generowanie trasy acji. Ponieważ strony mogą być dodawane na bieżąco potrzebne do dynamicznego generowania tras dla tych stron i nie ma możliwości dowiedzenia się, ile poziomów głęboko strona może być zagnieżdżona

Jeśli więc zacząć od głównej: /

a następnie rozpocząć dodawanie stron tj

/artykuły/Artykuł 1/coś/coś-else/inny stwór

Jak można coś takiego osiągnąć z szynami routingu modelu?

Odpowiedz

2

Trzeba przeanalizować trasę samemu

map.connect '*url', :controller => 'pages', :action => 'show' 

Teraz trzeba mieć params[:url] dostępny w działaniu, która jest ścieżką żądanie jako tablica oddzielonych ukośników. Kiedy już znajdziesz te strunki, łatwo znajdziesz potrzebne modele.

To było z pamięci i minęło dużo czasu. Mam nadzieję, że to działa dla ciebie.

8

Jednym z rozwiązań tego problemu jest dynamiczne ładowanie tras z zaczepów w modelach.Od przykład fragment z modelu Slug na mojej stronie:

class Slug < ActiveRecord::Base 

    belongs_to :navigable 

    validates_presence_of :name, :navigable_id 
    validates_uniqueness_of :name 

    after_save :update_route 

    def add_route 
    new_route = ActionController::Routing::Routes.builder.build(name, route_options) 
    ActionController::Routing::Routes.routes.insert(0, new_route) 
    end 

    def remove_route 
    ActionController::Routing::Routes.routes.reject! { |r| r.instance_variable_get(:@requirements)[:slug_id] == id } 
    end 

    def update_route 
    remove_route 
    add_route 
    end 

    def route_options 
    @route_options ||= { :controller  => navigable.controller, 
         :action   => navigable.action, 
         :navigable_id => navigable_id, 
         :slug_id  => id } 
    end 

end 

to wstawienie trasę na najwyższym priorytecie (0 w tablicy routingu w pamięci) po tym jak został zapisany.

Wygląda na to, że powinieneś używać wtyczki do zarządzania drzewem i lubisz wspaniały zestaw zagnieżdżony lub lepiej zagnieżdżony zestaw do zarządzania drzewem witryny.

0

Spójrz na źródła RadiantCMS, implementują tę funkcjonalność, o ile rozumiem ich własny opis.

9

Gdy masz jakiś sposób, aby wygenerować ciąg adres URL Page zapisów (i Zostawię tę część do ciebie), można po prostu map każdą stronę w config/routes.rb:

Page.all.each do |page| 
    map.connect page.url, :controller => 'pages', :action => 'show', :id => page 
end 

i mają obserwator hak modelu strony, aby przeładować tras gdy coś się zmienia:

class PageObserver < ActiveRecord::Observer 
    def reload_routes(page) 
    ActionController::Routing::Routes.reload! 
    end 
    alias_method :after_save, :reload_routes 
    alias_method :after_destroy, :reload_routes 
end 

nie zapomnij edytować config/environment.rb załadować obserwatora:

# Activate observers that should always be running 
config.active_record.observers = :page_observer 
+0

To świetne rozwiązanie, ale jak przekonwertowałbyś go na polecenia 3 pasujące do szyny? – Rumpleteaser

+1

inKit: 'match page.url => 'pages # show',: id => page.id' –

+1

Jeśli używasz szyn 3, przeładuj swoje trasy za pomocą' MyApplication :: Application.reload_routes! ' – dhulihan

0

Zaimplementowałam podobną funkcjonalność w klejnocie Railsów, korzystając z samo referencyjnych asocjacji i drzewa podobnego do js do zmiany kolejności i zagnieżdżania "stron".

Język szablonowania i uwierzytelnianie/autoryzacja pozostawia się programistom do wdrożenia. https://github.com/maca/tiny_cms