Exemplo n.º 1
0
		/// <summary>
		/// Embeds values for the given subject and property into the given output
		/// during the framing algorithm.
		/// </summary>
		/// <remarks>
		/// Embeds values for the given subject and property into the given output
		/// during the framing algorithm.
		/// </remarks>
		/// <param name="state">the current framing state.</param>
		/// <param name="element">the subject.</param>
		/// <param name="property">the property.</param>
		/// <param name="output">the output.</param>
		private void EmbedValues(JsonLdApi.FramingContext state, JObject element, string property, JToken output)
		{
			// embed subject properties in output
			JArray objects = (JArray)element[property];
			foreach (JToken o in objects)
			{
                var eachObj = o;

                if (eachObj is JObject && ((JObject)eachObj).ContainsKey("@list"))
                {
                    JObject list = new JObject { { "@list", new JArray() } };
                    if (output is JArray)
                    {
                        ((JArray)output).Add(list);
                    }
                    else
                    {
                        output[property] = new JArray(list);
                    }
                    EmbedValues(state, (JObject)eachObj, "@list", list["@list"]);
                }
                // handle subject reference
                else if (JsonLdUtils.IsNodeReference(eachObj))
				{
					string sid = (string)((JObject)eachObj)["@id"];
					// embed full subject if isn't already embedded
					if (!state.embeds.ContainsKey(sid))
					{
						// add embed
						JsonLdApi.EmbedNode embed = new JsonLdApi.EmbedNode(this);
						embed.parent = output;
						embed.property = property;
						state.embeds[sid] = embed;
						// recurse into subject
						eachObj = new JObject();
						JObject s = (JObject)this.nodeMap[sid];
						if (s == null)
						{
							s = new JObject();
							s["@id"] = sid;
						}
						foreach (string prop in s.GetKeys())
						{
							// copy keywords
							if (JsonLdUtils.IsKeyword(prop))
							{
								((JObject)eachObj)[prop] = JsonLdUtils.Clone(s[prop]);
								continue;
							}
							EmbedValues(state, s, prop, eachObj);
						}
					}
					AddFrameOutput(state, output, property, eachObj);
				}
				else
				{
					// copy non-subject value
					AddFrameOutput(state, output, property, JsonLdUtils.Clone(eachObj));
				}
			}
		}
Exemplo n.º 2
0
		/// <summary>Frames subjects according to the given frame.</summary>
		/// <remarks>Frames subjects according to the given frame.</remarks>
		/// <param name="state">the current framing state.</param>
		/// <param name="subjects">the subjects to filter.</param>
		/// <param name="frame">the frame.</param>
		/// <param name="parent">the parent subject or top-level array.</param>
		/// <param name="property">the parent property, initialized to null.</param>
		/// <exception cref="JSONLDProcessingError">JSONLDProcessingError</exception>
		/// <exception cref="JsonLD.Core.JsonLdError"></exception>
		private void Frame(JsonLdApi.FramingContext state, JObject nodes
			, JObject frame, JToken parent, string property)
		{
			// filter out subjects that match the frame
			JObject matches = FilterNodes(state, nodes, frame);
			// get flags for current frame
			bool embedOn = GetFrameFlag(frame, "@embed", state.embed);
			bool explicitOn = GetFrameFlag(frame, "@explicit", state.@explicit);
			// add matches to output
			JArray ids = new JArray(matches.GetKeys());
			ids.SortInPlace();
			foreach (string id in ids)
			{
				if (property == null)
				{
					state.embeds = new Dictionary<string, JsonLdApi.EmbedNode>();
				}
				// start output
				JObject output = new JObject();
				output["@id"] = id;
				// prepare embed meta info
				JsonLdApi.EmbedNode embeddedNode = new JsonLdApi.EmbedNode(this);
				embeddedNode.parent = parent;
				embeddedNode.property = property;
				// if embed is on and there is an existing embed
				if (embedOn && state.embeds.ContainsKey(id))
				{
					JsonLdApi.EmbedNode existing = state.embeds[id];
					embedOn = false;
					if (existing.parent is JArray)
					{
						foreach (JToken p in (JArray)(existing.parent))
						{
							if (JsonLdUtils.CompareValues(output, p))
							{
								embedOn = true;
								break;
							}
						}
					}
					else
					{
						// existing embed's parent is an object
						if (((JObject)existing.parent).ContainsKey(existing.property))
						{
							foreach (JToken v in (JArray)((JObject)existing.parent)[existing.property])
							{
								if (v is JObject && ((JObject)v)["@id"].SafeCompare(id))
								{
									embedOn = true;
									break;
								}
							}
						}
					}
					// existing embed has already been added, so allow an overwrite
					if (embedOn)
					{
						RemoveEmbed(state, id);
					}
				}
				// not embedding, add output without any other properties
				if (!embedOn)
				{
					AddFrameOutput(state, parent, property, output);
				}
				else
				{
					// add embed meta info
					state.embeds[id] = embeddedNode;
					// iterate over subject properties
					JObject element = (JObject)matches[id];
					JArray props = new JArray(element.GetKeys());
					props.SortInPlace();
					foreach (string prop in props)
					{
						// copy keywords to output
						if (JsonLdUtils.IsKeyword(prop))
						{
							output[prop] = JsonLdUtils.Clone(element[prop]);
							continue;
						}
						// if property isn't in the frame
						if (!frame.ContainsKey(prop))
						{
							// if explicit is off, embed values
							if (!explicitOn)
							{
								EmbedValues(state, element, prop, output);
							}
							continue;
						}
						// add objects
						JArray value = (JArray)element[prop];
						foreach (JToken item in value)
						{
							// recurse into list
                            if ((item is JObject) && ((JObject)item).ContainsKey("@list"))
							{
								// add empty list
								JObject list = new JObject();
								list["@list"] = new JArray();
								AddFrameOutput(state, output, prop, list);
								// add list objects
                                foreach (JToken listitem in (JArray)((JObject)item)["@list"
									])
								{
									// recurse into subject reference
									if (JsonLdUtils.IsNodeReference(listitem))
									{
										JObject tmp = new JObject();
                                        string itemid = (string)((IDictionary<string, JToken>)listitem)["@id"];
										// TODO: nodes may need to be node_map,
										// which is global
										tmp[itemid] = this.nodeMap[itemid];
                                        Frame(state, tmp, (JObject)((JArray)frame[prop])[0], list
											, "@list");
									}
									else
									{
										// include other values automatcially (TODO:
										// may need JsonLdUtils.clone(n))
										AddFrameOutput(state, list, "@list", listitem);
									}
								}
							}
							else
							{
								// recurse into subject reference
								if (JsonLdUtils.IsNodeReference(item))
								{
                                    JObject tmp = new JObject();
                                    string itemid = (string)((JObject)item)["@id"];
									// TODO: nodes may need to be node_map, which is
									// global
									tmp[itemid] = this.nodeMap[itemid];
									Frame(state, tmp, (JObject)((JArray)frame[prop])[0], output
										, prop);
								}
								else
								{
									// include other values automatically (TODO: may
									// need JsonLdUtils.clone(o))
									AddFrameOutput(state, output, prop, item);
								}
							}
						}
					}
					// handle defaults
					props = new JArray(frame.GetKeys());
					props.SortInPlace();
					foreach (string prop_1 in props)
					{
						// skip keywords
						if (JsonLdUtils.IsKeyword(prop_1))
						{
							continue;
						}
						JArray pf = (JArray)frame[prop_1];
						JObject propertyFrame = pf.Count > 0 ? (JObject)pf[0] : null;
						if (propertyFrame == null)
						{
							propertyFrame = new JObject();
						}
						bool omitDefaultOn = GetFrameFlag(propertyFrame, "@omitDefault", state.omitDefault
							);
						if (!omitDefaultOn && !output.ContainsKey(prop_1))
						{
							JToken def = "@null";
							if (propertyFrame.ContainsKey("@default"))
							{
								def = JsonLdUtils.Clone(propertyFrame["@default"]);
							}
							if (!(def is JArray))
							{
								JArray tmp = new JArray();
								tmp.Add(def);
								def = tmp;
							}
							JObject tmp1 = new JObject();
							tmp1["@preserve"] = def;
							JArray tmp2 = new JArray();
							tmp2.Add(tmp1);
							output[prop_1] = tmp2;
						}
					}
					// add output to parent
					AddFrameOutput(state, parent, property, output);
				}
			}
		}