2016-03-19 15 views
2

Ben aşağıdaki alanları olan bir Damage tablo vardır:JSON nesneleri dizisi olan bir ray alanı mı?

  • açıklama
  • date_of_damage

Ben şuna benzer JSON nesneleri Damagepoints saklamak için başka bir alan eklemek istiyorum :

{ top: 50, left: 100 } 

Üst ve sol bir üzerinde damagepoint koordinatları diyagram. damagepoints, kullanıcı tarafından Javascript kullanılarak eklenir/kaldırılır.

Ancak, bu gibi bir alanda, bu damagepoints bir dizi saklamak istediğinizi: Bir has_many ilişki nedeniyle bir Damagepoint tablosu kullanılarak bunu yapmak istemiyorum

@damage.damagepoints = [{left: 40, top: 99}, {left: 100, top: 35}, {left: 150, top: 95}] 

Bu değişikliklerin tümü Javascript kullanılarak yapılacaktır ve kullanıcı tarafından Damagepoints oluşturulduğunda veya kaldırıldığında, sadece damagepoints güncellenmiş dizisini istemciden geçirmek ve veritabanındaki eski diziyi yeni diziyle değiştirmek istiyorum. Bir has_many ilişkisi kullanmış olsaydım, Damagepoints'un tümünü silmem ve dizinin her güncelleştirilmesinde her yeni bir tane oluşturmam gerekir (çünkü çok karmaşıktır ve ben yokken belirli hasar noktalarını silmekten/eklememden bir yararım yok) tarih izlemeniz gerekir.

@damage.damagepoints (yukarıda) gibi verileri depolamanın en kolay yolu nedir? Tek yapmam gereken, onu (denetleyici aracılığıyla) bir html5 veri özniteliğine geçirmektir, böylece Javascript tarafından mevcut damagepoints şemasına (koordinatlarına dayanarak) eklenebilir ve sonra güncelleştirilmiş bir diziyi iletebilir (html5 veri özniteliğinden), kullanıcı 'Kaydet' düğmesini tıkladığında bir AJAX çağrısı aracılığıyla denetleyiciye geri döner.

Rails 4.2 ve Postresql kullanıyorum.

Teşekkürler! Veritabanına yazmadan önce verilerinizi seri hale getirin ve okurken serileştirin.

cevap

6

Postgres'i kullanırken şanslısınız: postgres, yerel bir json türüne sahip. Bu, veriyi kodlanmış dizenin bir biçimi olarak saklamak için serileştirmenin kullanılmasından daha iyidir, çünkü postgres'in bu json verilerine karşı sorgulamanıza izin veren zengin bir işleç ailesi vardır.

Eğer 9.4 postgres kullanıyorsanız, jsonb tipini de kullanabilirsiniz.Bu genellikle verilerin işlenmiş bir versiyonunu depoladığı (yani tekrar tekrar veriyi tekrar tekrar tutmak zorunda kalmayacağı) ve indekse izin verdiği için daha iyidir.

Rails bunu kutudan çıkarır (bkz. here), yalnızca json (b) tipi bir sütun eklemeniz gerekir. Taşıma

create_table :damages do |t| 
    t.string :description 
    t.jsonb :damage_points 
end 

içeriyorsa o zaman

Damage.create(damage_points: [{left: 40, top: 99}, {left: 100, top: 35}]) 

json olarak hasar noktaları veri deposuna sahip bir satır yaratacak. Dikkat edilmesi gereken tek şey, giriş verileriniz karma anahtarlardaki semboller olsa da, veritabanından getirilirken her zaman anahtar olarak geri dizeleri alacağınızdır.

+0

kabul eder Teşekkürler! Kullanıcı, bir AJAX çağrısı aracılığıyla bir kontrol dizisi olarak denetleyiciye aktarılan 'damage_points'de değişiklik yaparsa, 'Damage.damage_points = nil' ve ardından 'Damage.create' ı (damage_points) ayarlayabilirim. : [{...}] '? Ben kazanmak için küçük bir sürü sorun olacak gibi, belirli damage_points oluşturmak veya silmek zorunda kalmak istemiyorum.Teşekkürler! – jackerman09

+0

Evet - damage_points yeniden atama zaten ne olduğunu tamamen üzerine yazacaktır İlk olarak sıfırlamaya gerek yok. –

+0

Harika, tekrar teşekkürler! – jackerman09

1
Modeldeki alıcı ve ayarlayıcıyı geçersiz kılabilirsiniz.

Serileştirme için iki iyi seçenek JSON ve YAML olacaktır.

Raylar json gemiyle birlikte gelir; böylece herhangi bir nesne veya dizide to_json'u arayabilirsiniz. O zaman okumak zorundasınız, JSON.parse(some_json).

Benzer şekilde, Raylar yaml ile birlikte gelir; böylece YAML.dump(text) ve YAML.load(text)'u kullanabilirsiniz. YAML benim görüşüme göre JSON'dan biraz daha insan tarafından okunabilir, ancak verileri Javascript'e aktarıyorsanız, JSON standarttır.

+0

Veritabanında normal bir 'string' alanını kullanır mıyım? – jackerman09

+0

'text' aslında, daha uzun bir dize –