[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Newsgroup Home]
[news.eclipse.modeling.m2m] Re: [ATL] How to put model elements in a package that is created in another rule?

Hello,

> I already found out how to do this using lazy rules.
>
> Now I have one matched rule and two lazy rules.
> Comments on how to do this in a better way are welcome of course.

Your solution with lazy rules should not actually need the rules to be lazy to work. Therefore, you could also use:

rule struct {
   from
           b : BoxMM!Box
   to
           m : UML!Model (
               name<- b.name
           ),
           ps : UML!Package (
               name<-'squares',
               namespace<-m,
               ownedElement<-BoxMM!Square.allInstances()
           ),
           pc : UML!Package (
               name <-'circles',
               namespace <-m,
               ownedElement<-BoxMM!Circle.allInstances()
           )
}

rule squares {
    from
        s : BoxMM!Square
    to
        c : UML!Class (
            name<-s.name
        )
}

rule circles {
    from
        s : BoxMM!Circle
    to
        c : UML!Class (
            name<-s.name
        )
}


This works because source elements are automatically resolved into their corresponding target elements.


Both your lazy rules solution, and the one above initialize the ownedElement reference. You can also initialize the namespace reference as you attempted to do in your previous code excerpt:

rule struct {
    from
            b : BoxMM!Box
    to
            m : UML!Model (
                name<- b.name
            ),
            ps : UML!Package (
                name<-'squares',
                namespace<-m
            ),
            pc : UML!Package (
                name <-'circles',
                namespace <-m
            )
}


rule squares {
from
s : BoxMM!Square
to
c : UML!Class (
name<-s.name,
namespace <-thisModule.resolveTemp(<an expression to get the box>, 'ps')
)
}



Where <an expression to get the box> may be any expression that can retrieve the Box. For instance, if a square has a reference myBox to its box, then you can use:


            namespace <-thisModule.resolveTemp(s.myBox, 'ps')

If the square is directly contained in the box, then you can also use:

namespace <-thisModule.resolveTemp(s.refImmediateComposite(), 'ps')

Otherwise, you may need to write a recursive helper to get the box.



There is another alternative that does not make use of resolveTemp: using unique lazy rules.



rule struct {
    from
            b : BoxMM!Box
    to
            m : UML!Model (
                name<- b.name
            )
}

unique lazy rule squaresPackage {
    from
            b : BoxMM!Box
    to
            ps : UML!Package (
                name<-'squares',
                namespace<-b	-- will be resolved into the Model
            )
)

unique lazy rule circlesPackage {
    from
            b : BoxMM!Box
    to
            pc : UML!Package (
                name <-'circles',
                namespace <-b	-- will be resolved into the Model
            )
}


rule squares {
from
s : BoxMM!Square
to
c : UML!Class (
name<-s.name,
namespace <-thisModule.squaresPackage(<an expression to get the box>, 'ps')
)
}


Note that you also need to get the box from the squares in this solution.


Regards,

Frédéric Jouault