Aviso de que este post no es un tutorial. Son los pasos (o palos) que voy dando para adentrarme en el mundo de node y mongo. Si lo sigues paso a paso irás fallando como yo lo he hecho... pero al menos habrás probado.
La situación que me planteo es la siguiente:
Un restaurante dividido en zonas, cada zona con sus mesas.Necesito un historial de cada mesa con los artículos que vayan pidiendo los clientes, los cuales pueden elegir entre un menú de carne o pescado.
Más o menos estas son las colecciones que necesito:
articulos: id, nombre, familia
mesas: id, nombre, zona
historial: id, fecha, mesa, descrip ( linea, articulo, precio)
Al lío:
> use km
switched to db km
km.articulos
> a = db.articulos
km.articulos
> a.find();
> a.insert({_id:1, nombre: 'Churrasco', familia: 'Carnes'});
> a.insert({_id:2, nombre: 'Kobe', familia: 'Carnes'});
> a.insert({_id:3, nombre: 'Solomillo de Ternera', familia: 'Carnes'});
> a.insert({_id:4, nombre: 'Dorada', familia: 'Pescado'});
> a.insert({_id:5, nombre: 'Urta', familia: 'Pescado'});
Ahora las mesas:
> var m = db.mesas
> m.insert({_id:1, nombre:'1', zona:'Salon'});
> m.insert({_id:2, nombre:'2', zona:'Salon'});
> m.insert({_id:3, nombre:'3', zona:'Salon'});
> m.insert({_id:4, nombre:'4', zona:'Terraza'});
> m.insert({_id:5, nombre:'5', zona:'Terraza'});
> m.insert({_id:6, nombre:'6', zona:'Terraza'});
> a.find();
{ "_id" : 1, "nombre" : "Churrasco", "familia" : "Carnes" }
{ "_id" : 2, "nombre" : "Kobe", "familia" : "Carnes" }
{ "_id" : 3, "nombre" : "Solomillo de Ternera", "familia" : "Carnes" }
{ "_id" : 4, "nombre" : "Dorada", "familia" : "Pescado" }
{ "_id" : 5, "nombre" : "Urta", "familia" : "Pescado" }
> m.find();
{ "_id" : 1, "nombre" : "1", "zona" : "Salon" }
{ "_id" : 2, "nombre" : "2", "zona" : "Salon" }
{ "_id" : 3, "nombre" : "3", "zona" : "Salon" }
{ "_id" : 4, "nombre" : "4", "zona" : "Terraza" }
{ "_id" : 5, "nombre" : "5", "zona" : "Terraza" }
{ "_id" : 6, "nombre" : "6", "zona" : "Terraza" }
> var h = db.historial;
- El camarero lleva a sus clientes a la mesa 5. Lo primero que tiene que hacer es visualizar las mesas que hay en la zona 'Terraza' para poder visualizar la mesa que necesita:
{ "_id" : 4, "nombre" : "4", "zona" : "Terraza" }
{ "_id" : 5, "nombre" : "5", "zona" : "Terraza" }
{ "_id" : 6, "nombre" : "6", "zona" : "Terraza" }
> h.insert({_id:1, fecha:new Date(2013,4,10), mesa:'5'});
Al definir la colección 'articulos' se me pasó añadir una clave 'precio'. Necesito crear el campo 'precio' en 'articulos`' (los pondré todos al mismo precio):
>a.update({},{'$set':{precio:8.60}}, false, true);
> var pvp=a.find({nombre:'Churrasco'}, {precio:1});
> h.update({_id:1},{'$set': {descrip:[{linea: 1, articulo: 'Churrasco', precio: pvp}]}});
> h.find();
{ "_id" : 1, "descrip" : [ { "linea" : 1, "articulo" : "Churrasco"
, "precio" : { "_mongo" : { "slaveOk" : false, "host" : "127.0.
0.1" }, "_db" : { "_mongo" : { "slaveOk" : false, "host" :
"127.0.0.1" }, "_name" : "km" }, "_collection" : { "_mongo"
: { "slaveOk" : false, "host" : "127.0.0.1" }, "_db" : {
"_mongo" : { "slaveOk" : false, "host" : "127.0.0.1" }, "_name"
: "km" }, "_shortName" : "articulos", "_fullName" : "km.articulos",
"_lastID" : 5 }, "_ns" : "km.articulos", "_query" : { "nombre"
: "Churrasco" }, "_fields" : { "precio" : 1 }, "_limit" : 0,
"_skip" : 0, "_batchSize" : 0, "_options" : 0, "_cursor" : null
, "_numReturned" : 0, "_special" : false } } ], "fecha" : ISODate("201
3-05-09T22:00:00Z"), "mesa" : "5" }
Borro los documentos de la coleccion 'historial':
>db.historial.remove();
> h.find();
Inserto un historial nuevo:
> h.insert({_id:1, fecha:new Date(2013,4,5,17,25), mesa:'5'});
> h.find();
{ "_id" : 1, "fecha" : ISODate("2013-05-05T15:25:00Z"), "mesa" : "5" }
> h.update({_id:1},{'$set':{descrip:[{linea:1, articulo:'Churrasco', precio: 8.60}]}});
> h.find();
{ "_id" : 1, "descrip" : [ { "linea" : 1, "articulo" : "Churrasco", "precio" : 8
.6 } ], "fecha" : ISODate("2013-05-05T15:25:00Z"), "mesa" : "5" }
>
> var pvp=a.find({nombre:'Churrasco'}, {precio:1});
> h.update({_id:1},{'$push':{descrip:[{linea:2, articulo:'Churrasco', precio: pvp.precio}]}});
{ "_id" : 1, "descrip" :
[{"linea" : 1,"articulo" : "Churrasco","precio" : 8.6 }
,[{"linea" : 2,"articulo" : "Churrasco","precio" : null } ] ]
, "fecha" : ISODate("2013-05-05T15:25:00Z"), "mesa" : "5" }
> pvp
{ "_id" : 1, "precio" : 8.6 }
El _id no lo necesito para nada, ya que lo que usaré será el precio nada más:
{ "precio" : 8.6 }
> var pvp=db.articulos.find({nombre:'Churrasco'}, {precio:1, _id:0});
> pvp.hasNext();
true
> print(pvp);
DBQuery: km.articulos -> { "nombre" : "Churrasco" }
> print(pvp.next().precio);
8.6
> var arts = db.articulos.find({familia:'Carnes'});
> while(arts.hasNext()){printjson(arts.next().nombre)};
"Churrasco"
"Kobe"
"Solomillo de Ternera"
o bien:
> var arts = db.articulos.find({familia:'Carnes'});
> arts.forEach(printjson);
{ "_id" : 1, "familia" : "Carnes", "nombre" : "Churrasco", "precio" : 8.6 }
{ "_id" : 2, "familia" : "Carnes", "nombre" : "Kobe", "precio" : 8.6 }
{
"_id" : 3,
"familia" : "Carnes",
"nombre" : "Solomillo de Ternera",
"precio" : 8.6
}
Con todo esto, si quisiera agregar una nueva linea al pedido, pero esta vez usando el precio del articulo en una variable, hasta donde llego lo haría así:
> var pvp=a.find({nombre:'Churrasco'}, {precio:1});
> h.update({_id:1},{'$push':{descrip:[{linea:2, articulo:'Churrasco', precio: pv
p.next().precio}]}});
{
"_id" : 1,
"descrip" : [
{
"linea" : 1,
"articulo" : "Churrasco",
"precio" : null
},
[
{
"linea" : 2,
"articulo" : "Churrasco",
"precio" : null
}
],
[
{
"linea" : 2,
"articulo" : "Churrasco",
"precio" : 8.6
}
]
],
"fecha" : ISODate("2013-05-05T15:25:00Z"),
"mesa" : "5"
}
Ok. Me ha insertado el precio del churrasco pero:
1.Me he equivocado y he añadido una nueva descrip con el mismo numero de linea.
2.Veo muchos corchetes en el resultado... suponía que sólo debo verlos una vez dentro de 'descrip'.
Primero revisaré la estructura. Para comprobar si estoy en lo correcto: Crearé un nuevo documento en 'historial', insertando dos lineas 'descrip' para ver si todo queda dentro de los corchetes:
> h.insert({_id:2, fecha: new Date(2013/04/10), mesa:'4', descrip:[{linea:1, art
iculo:'Churrasco', precio: 8.6},{linea:2, articulo:'Kobe', precio:8.6}]});
> h.find({_id:2}).pretty();
{
"_id" : 2,
"fecha" : ISODate("1970-01-01T00:00:00.050Z"),
"mesa" : "4",
"descrip" : [
{
"linea" : 1,
"articulo" : "Churrasco",
"precio" : 8.6
},
{
"linea" : 2,
"articulo" : "Kobe",
"precio" : 8.6
}
]
Este resultado me cuadra más (la fecha evidentemente no, pero he probado a introducirla de otra forma y ha salido esa). Seguramente me habré equivocado al hacer el $set o el $push... así que a probarlo de nuevo, a ver si al actualizar sigue todo dentro del mismo array 'descrip':
> h.insert({_id:3, fecha: new Date(), mesa:'4'});
> h.update({_id:3},{'$push':{descrip:{linea:1, articulo:'Churrasco', precio:8.6}}});
> h.update({_id:3},{'$push':{descrip:{linea:2, articulo:'Kobe', precio:8.6}}});
Lo compruebo:
> h.find({_id:3}).pretty();
{
"_id" : 3,
"descrip" : [
{
"linea" : 1,
"articulo" : "Churrasco",
"precio" : 8.6
},
{
"linea" : 2,
"articulo" : "Kobe",
"precio" : 8.6
}
],
"fecha" : ISODate("2013-04-10T18:27:15.796Z"),
"mesa" : "4"
}
Ahora sí me cuadra... Me cuadra hasta la fecha. Las líneas de 'descrip' están entre llaves, NO entre corchetes como aparecían al principio.
Lo único que no cuadra es el primer documento, ya que aparecen las lineas de descripción entre corchetes.
Así que lo borro y listo. Podía haber tratado de modificarlo, pero por hoy ya he tenido suficiente. Así que mañana será otro día y trataré de avanzar un poco más sobre el tema.