211 <xsl:with-param name="up" select="$up"/> |
211 <xsl:with-param name="up" select="$up"/> |
212 <xsl:with-param name="down" select="$down"/> |
212 <xsl:with-param name="down" select="$down"/> |
213 <xsl:with-param name="replaces" select="$replaces"/> |
213 <xsl:with-param name="replaces" select="$replaces"/> |
214 </xsl:apply-templates> |
214 </xsl:apply-templates> |
215 |
215 |
216 |
|
217 <!-- tack on any remaining layers --> |
216 <!-- tack on any remaining layers --> |
218 <xsl:apply-templates mode="merge-copy-of" select="$other/systemModel/layer[not(@before) and not(following-sibling::*[@id=current()/layer/@id]) and not(@id=current()/layer/@id)]"> |
217 <xsl:apply-templates mode="merge-copy-of" select="$other/systemModel/layer[not(@before) and not(following-sibling::*[@id=current()/layer/@id]) and not(@id=current()/layer/@id)]"> |
219 <xsl:with-param name="origin" select="$down"/> |
218 <xsl:with-param name="origin" select="$down"/> |
220 <xsl:with-param name="root" select="current()/.."/> |
219 <xsl:with-param name="root" select="current()/.."/> |
221 <xsl:with-param name="replaces" select="$replaces"/> |
220 <xsl:with-param name="replaces" select="$replaces"/> |
271 <xsl:param name="remainder" select="/.."/> |
270 <xsl:param name="remainder" select="/.."/> |
272 |
271 |
273 <xsl:choose> |
272 <xsl:choose> |
274 <xsl:when test="not($to-sort)"/> <!-- nothing left to copy. stop --> |
273 <xsl:when test="not($to-sort)"/> <!-- nothing left to copy. stop --> |
275 <xsl:when test="not($base)"/> <!-- reached end. stop --> |
274 <xsl:when test="not($base)"/> <!-- reached end. stop --> |
276 <xsl:when test="$base[1]/@id=$end/following-sibling::*[1]/@id"/> <!-- passed $end. Stop --> |
275 <xsl:otherwise> |
277 <xsl:when test="$base[1]/@id = $to-sort[1]/@id"> <!-- both lists start with same item --> |
276 <xsl:for-each select="$to-sort"> |
278 <xsl:if test="$base[1]/@id!=$end/@id"> <!-- not at end, so keep going --> |
277 <xsl:if test="((@before=$end/@id) or not(@before) or not($base/ancestor::SystemDefinition//*[@id=current()/@before])) and not($base[@id=current()/@id])"> |
279 <xsl:call-template name="copy-sorted-content"> |
278 <xsl:apply-templates mode="merge-copy-of" select="."> |
280 <xsl:with-param name="base" select="$base[position() != 1]"/> |
279 <xsl:with-param name="origin" select="$down"/> |
281 <xsl:with-param name="to-sort" select="$to-sort[position() != 1]"/> |
280 <xsl:with-param name="root" select="$end/ancestor::SystemDefinition"/> |
282 <xsl:with-param name="remainder" select="$remainder"/> |
281 </xsl:apply-templates> |
283 <xsl:with-param name="start" select="$start"/> |
282 </xsl:if> |
284 <xsl:with-param name="end" select="$end"/> |
283 </xsl:for-each> |
285 <xsl:with-param name="down" select="$down"/> |
284 </xsl:otherwise> |
286 </xsl:call-template> |
|
287 </xsl:if> |
|
288 </xsl:when> |
|
289 <xsl:when test="$remainder[@id = $base[1]/@id]"> <!-- left over item is in $base --> |
|
290 <xsl:call-template name="copy-sorted-content"> |
|
291 <xsl:with-param name="base" select="$base[position() != 1]"/> |
|
292 <xsl:with-param name="to-sort" select="$to-sort"/> |
|
293 <xsl:with-param name="remainder" select="$remainder[@id != $base[1]/@id]"/> |
|
294 <xsl:with-param name="start" select="$start"/> |
|
295 <xsl:with-param name="end" select="$end"/> |
|
296 <xsl:with-param name="down" select="$down"/> |
|
297 </xsl:call-template> |
|
298 </xsl:when> |
|
299 <xsl:when test="not($base[@id = $to-sort[1]/@id])"> <!-- in to-sort, but not base --> |
|
300 <xsl:if test="$base[1]/@id=$end/@id and not($base[@id=$to-sort[1]/@before])"> |
|
301 <!-- if at end, then this needs to be copied |
|
302 don't copy if the before ID is found in $base --> |
|
303 <xsl:apply-templates mode="merge-copy-of" select="$to-sort[1]"> |
|
304 <xsl:with-param name="origin" select="$down"/> |
|
305 <xsl:with-param name="root" select="$end/ancestor::SystemDefinition"/> |
|
306 </xsl:apply-templates> |
|
307 </xsl:if> |
|
308 <xsl:call-template name="copy-sorted-content"> |
|
309 <xsl:with-param name="base" select="$base"/> |
|
310 <xsl:with-param name="to-sort" select="$to-sort[position() != 1]"/> |
|
311 <xsl:with-param name="remainder" select="$remainder"/> |
|
312 <xsl:with-param name="start" select="$start"/> |
|
313 <xsl:with-param name="end" select="$end"/> |
|
314 <xsl:with-param name="down" select="$down"/> |
|
315 </xsl:call-template> |
|
316 </xsl:when> |
|
317 <xsl:when test="not($to-sort[@id = $base[1]/@id])"> <!-- in base, but not to-sort --> |
|
318 <xsl:call-template name="copy-sorted-content"> |
|
319 <xsl:with-param name="base" select="$base[position() != 1]"/> |
|
320 <xsl:with-param name="to-sort" select="$to-sort"/> |
|
321 <xsl:with-param name="remainder" select="$remainder"/> |
|
322 <xsl:with-param name="start" select="$start"/> |
|
323 <xsl:with-param name="end" select="$end"/> |
|
324 <xsl:with-param name="down" select="$down"/> |
|
325 </xsl:call-template> |
|
326 </xsl:when> |
|
327 <xsl:when test="$base[@id = $to-sort[1]/@id]"> <!-- is in base, but not 1st one--> |
|
328 <xsl:call-template name="copy-sorted-content"> |
|
329 <xsl:with-param name="base" select="$base"/> |
|
330 <xsl:with-param name="to-sort" select="$to-sort[position() != 1] "/> |
|
331 <xsl:with-param name="remainder" select="$remainder | $to-sort[1]"/> |
|
332 <xsl:with-param name="start" select="$start"/> |
|
333 <xsl:with-param name="end" select="$end"/> |
|
334 <xsl:with-param name="down" select="$down"/> |
|
335 </xsl:call-template> |
|
336 </xsl:when> |
|
337 </xsl:choose> |
285 </xsl:choose> |
338 </xsl:template> |
286 </xsl:template> |
339 |
287 |
340 <xsl:template match="node()" mode="merge-data"> |
288 <xsl:template match="node()" mode="merge-data"> |
341 <xsl:copy-of select="." /> |
289 <xsl:copy-of select="." /> |
372 <xsl:apply-templates select="node()" mode="as-xml-text"/> |
320 <xsl:apply-templates select="node()" mode="as-xml-text"/> |
373 <xsl:value-of select="concat('</',name(),'>')"/> |
321 <xsl:value-of select="concat('</',name(),'>')"/> |
374 </xsl:template> |
322 </xsl:template> |
375 |
323 |
376 |
324 |
|
325 <xsl:template name="best-prev"><xsl:param name="cur" select="."/><xsl:param name="alt"/> |
|
326 <xsl:if test="$alt"> |
|
327 <xsl:variable name="prev" select="$cur/preceding-sibling::*[@id][1]"/> |
|
328 <xsl:choose> |
|
329 <xsl:when test="not($prev)"/> |
|
330 <xsl:when test="$alt/preceding-sibling::*[@id=$prev/@id]"><xsl:value-of select="$prev/@id"/></xsl:when> |
|
331 <xsl:otherwise> |
|
332 <xsl:call-template name="best-prev"> |
|
333 <xsl:with-param name="cur" select="$prev"/> |
|
334 <xsl:with-param name="alt" select="$alt"/> |
|
335 </xsl:call-template> |
|
336 </xsl:otherwise> |
|
337 </xsl:choose> |
|
338 </xsl:if> |
|
339 </xsl:template> |
|
340 |
377 <xsl:template match="layer | package | collection | component" mode="merge-models"> |
341 <xsl:template match="layer | package | collection | component" mode="merge-models"> |
378 <xsl:param name="other"/> <!-- the downstream item of the parent's rank that contains a potential items this is merged with --> |
342 <xsl:param name="other"/> <!-- the downstream item of the parent's rank that contains a potential items this is merged with --> |
379 <xsl:param name="up"/> |
343 <xsl:param name="up"/> |
380 <xsl:param name="down"/> |
344 <xsl:param name="down"/> |
381 <xsl:param name="replaces"/> |
345 <xsl:param name="replaces"/> |
384 <xsl:variable name="match" select="$other/*[@id=current()/@id]"/> |
348 <xsl:variable name="match" select="$other/*[@id=current()/@id]"/> |
385 |
349 |
386 <xsl:choose> |
350 <xsl:choose> |
387 <xsl:when test="$replaces[.=$this/@id] or (self::component and $match)"> <!-- replace the item instead of merge --> |
351 <xsl:when test="$replaces[.=$this/@id] or (self::component and $match)"> <!-- replace the item instead of merge --> |
388 <xsl:message>Note: <xsl:value-of select="name()"/> "<xsl:value-of select="@id"/>" in "<xsl:value-of select="../@id"/>" <xsl:choose> |
352 <xsl:message>Note: <xsl:value-of select="name()"/> "<xsl:value-of select="@id"/>" in "<xsl:value-of select="../@id"/>" <xsl:choose> |
389 <xsl:when test="self::component and $match">overridden in downstream sysdef</xsl:when> |
353 <xsl:when test="self::component and $match">overridden in downstream sysdef</xsl:when> |
390 <xsl:otherwise><xsl:for-each select="$replaces[.=$this/@id]/..">replaced by <xsl:value-of select="name()"/> "<xsl:value-of select="@id"/>" in "<xsl:value-of select="../@id"/>"</xsl:for-each></xsl:otherwise> |
354 <xsl:otherwise><xsl:for-each select="$replaces[.=$this/@id]/..">replaced by <xsl:value-of select="name()"/> "<xsl:value-of select="@id"/>" in "<xsl:value-of select="../@id"/>"</xsl:for-each></xsl:otherwise> |
391 </xsl:choose> |
355 </xsl:choose> |
392 </xsl:message> |
356 </xsl:message> |
393 <!-- if the removed item is in the downstream doc, just copy that and ignore the upstream contents --> |
357 <!-- if the removed item is in the downstream doc, just copy that and ignore the upstream contents --> |
394 <xsl:apply-templates mode="merge-copy-of" select="$match"> |
358 <xsl:apply-templates mode="merge-copy-of" select="$match"> |
395 <xsl:with-param name="origin" select="$down"/> |
359 <xsl:with-param name="origin" select="$down"/> |
396 <xsl:with-param name="root" select="$this/ancestor::SystemDefinition"/> |
360 <xsl:with-param name="root" select="$this/ancestor::SystemDefinition"/> |
398 </xsl:apply-templates> |
362 </xsl:apply-templates> |
399 </xsl:when> |
363 </xsl:when> |
400 <xsl:otherwise> |
364 <xsl:otherwise> |
401 <!-- remove this if it's in the list of stuff to be replaced--> |
365 <!-- remove this if it's in the list of stuff to be replaced--> |
402 |
366 |
|
367 <xsl:variable name="prev-id"> |
|
368 <xsl:call-template name="best-prev"> |
|
369 <xsl:with-param name="alt" select="$match"/> |
|
370 </xsl:call-template> |
|
371 </xsl:variable> |
|
372 |
403 <!-- prev = the previous item before the current one (no metas, only named items)--> |
373 <!-- prev = the previous item before the current one (no metas, only named items)--> |
404 <xsl:variable name="prev" select="preceding-sibling::*[@id][1]"/> |
374 <xsl:variable name="prev" select="preceding-sibling::*[@id=$prev-id]"/> |
405 |
375 |
406 <!-- copy all items between this and prev that are solely in the downstream model --> |
376 |
407 |
377 <!-- copy all items between this and prev that are solely in the downstream model --> |
408 <xsl:choose> |
378 |
409 <xsl:when test="$match and (not($prev) or $other/*[@id= $prev/@id] )"> |
379 <xsl:choose> |
|
380 <xsl:when test="$match and $prev"> |
410 <xsl:call-template name="copy-sorted-content"> |
381 <xsl:call-template name="copy-sorted-content"> |
411 <xsl:with-param name="base" select="../*[@id]"/> |
382 <xsl:with-param name="base" select="../*[@id]"/> |
412 <xsl:with-param name="to-sort" select="$other/*[@id]"/> |
383 <xsl:with-param name="to-sort" select="$other/*[@id][following-sibling::*[@id=$match/@id]][preceding-sibling::*[@id=$prev/@id]]"/> |
413 <xsl:with-param name="start" select="$prev"/> |
384 <xsl:with-param name="start" select="$prev"/> |
414 <xsl:with-param name="end" select="."/> |
385 <xsl:with-param name="end" select="."/> |
415 <xsl:with-param name="down" select="$down"/> |
386 <xsl:with-param name="down" select="$down"/> |
416 </xsl:call-template> |
387 </xsl:call-template> |
417 </xsl:when> |
388 </xsl:when> |
418 <xsl:when test="not($match/preceding-sibling::*[@id=$this/../*/@id]) and $other/*[@id= current()/@id]/preceding-sibling::*[@id and not(@before)]"> |
389 <xsl:when test="$match and not($prev)"> |
419 <!-- if this is the first item in other that's also in this, then put all new items from other here --> |
390 <xsl:call-template name="copy-sorted-content"> |
420 <xsl:apply-templates mode="merge-copy-of" select="$match/preceding-sibling::*[@id and not(@before)]"> |
391 <xsl:with-param name="base" select="../*[@id]"/> |
421 <xsl:with-param name="origin" select="$down"/> |
392 <xsl:with-param name="to-sort" select="$other/*[@id][following-sibling::*[@id=$match/@id]]"/> |
422 <xsl:with-param name="root" select="$this/ancestor::SystemDefinition"/> |
393 <xsl:with-param name="start" select="$prev"/> |
423 <xsl:with-param name="replaces" select="$replaces"/> |
394 <xsl:with-param name="end" select="."/> |
424 </xsl:apply-templates> |
395 <xsl:with-param name="down" select="$down"/> |
425 </xsl:when> |
396 </xsl:call-template> |
|
397 </xsl:when> |
426 </xsl:choose> |
398 </xsl:choose> |
427 |
399 |
428 <!-- just copy anything identified as being before this, assume they're all ok --> |
400 <!-- just copy anything identified as being before this, assume they're all ok --> |
429 <xsl:apply-templates mode="merge-copy-of" select="$other/*[@before=current()/@id]"> |
401 <xsl:apply-templates mode="merge-copy-of" select="$other/*[@before=current()/@id]"> |
430 <xsl:with-param name="remove-before" select="1"/> |
402 <xsl:with-param name="remove-before" select="1"/> |
431 <xsl:with-param name="origin" select="$down"/> |
403 <xsl:with-param name="origin" select="$down"/> |
432 <xsl:with-param name="root" select="$this/ancestor::SystemDefinition"/> |
404 <xsl:with-param name="root" select="$this/ancestor::SystemDefinition"/> |
433 <xsl:with-param name="replaces" select="$replaces"/> |
405 <xsl:with-param name="replaces" select="$replaces"/> |
434 </xsl:apply-templates> |
406 </xsl:apply-templates> |
435 |
|
436 |
407 |
437 <xsl:copy> |
408 <xsl:copy> |
438 <xsl:apply-templates select="@*" mode="merge-models"> <!-- copy upstream attributes --> |
409 <xsl:apply-templates select="@*" mode="merge-models"> <!-- copy upstream attributes --> |
439 <xsl:with-param name="other" select="$match"/> |
410 <xsl:with-param name="other" select="$match"/> |
440 </xsl:apply-templates> |
411 </xsl:apply-templates> |