1

我正在使用收入平台作为测试平台。我在单独的模块 Provider 中添加了一个实体。Provider 通过父属性引用了自身。我想确保在填写父字段时可以使用自动完成功能或能够从列表中选择提供者。每当我在 @DomainObject 注释中添加自动完成选项并引用 ProviderRepository 时,我都会收到如下构建错误。

    [DEBUG] Meta model invalid
org.apache.isis.core.metamodel.specloader.validator.MetaModelInvalidException: 1: @DomainObject annotation on domainapp.modules.provider.dom.Provider specifies unknown repository 'd
omainapp.modules.provider.dom.ProviderRepository'

        at org.apache.isis.core.metamodel.specloader.validator.ValidationFailures.assertNone(ValidationFailures.java:51)
        at org.apache.isis.core.metamodel.specloader.SpecificationLoader.validateAndAssert(SpecificationLoader.java:252)
        at org.apache.isis.core.runtime.system.session.IsisSessionFactoryBuilder$1.run(IsisSessionFactoryBuilder.java:206)
        at org.apache.isis.core.runtime.system.session.IsisSessionFactory$1.call(IsisSessionFactory.java:322)
        at org.apache.isis.core.runtime.system.session.IsisSessionFactory$1.call(IsisSessionFactory.java:319)
        at org.apache.isis.core.runtime.system.session.IsisSessionFactory.doInSession(IsisSessionFactory.java:353)
        at org.apache.isis.core.runtime.system.session.IsisSessionFactory.doInSession(IsisSessionFactory.java:319)
        at org.apache.isis.core.runtime.system.session.IsisSessionFactory.doInSession(IsisSessionFactory.java:306)
        at org.apache.isis.core.runtime.system.session.IsisSessionFactoryBuilder.buildSessionFactory(IsisSessionFactoryBuilder.java:201)
        at org.apache.isis.tool.mavenplugin.IsisMojoAbstract.execute(IsisMojoAbstract.java:65)
        at org.apache.maven.plugin.DefaultBuildPluginManager.executeMojo(DefaultBuildPluginManager.java:132)
        at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:208)
        at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:153)
        at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:145)
        at org.apache.maven.lifecycle.internal.LifecycleModuleBuilder.buildProject(LifecycleModuleBuilder.java:116)
        at org.apache.maven.lifecycle.internal.LifecycleModuleBuilder.buildProject(LifecycleModuleBuilder.java:80)
        at org.apache.maven.lifecycle.internal.builder.singlethreaded.SingleThreadedBuilder.build(SingleThreadedBuilder.java:51)
        at org.apache.maven.lifecycle.internal.LifecycleStarter.execute(LifecycleStarter.java:120)
        at org.apache.maven.DefaultMaven.doExecute(DefaultMaven.java:355)
        at org.apache.maven.DefaultMaven.execute(DefaultMaven.java:155)
        at org.apache.maven.cli.MavenCli.execute(MavenCli.java:584)
        at org.apache.maven.cli.MavenCli.doMain(MavenCli.java:216)
        at org.apache.maven.cli.MavenCli.main(MavenCli.java:160)
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
        at java.lang.reflect.Method.invoke(Method.java:498)
        at org.codehaus.plexus.classworlds.launcher.Launcher.launchEnhanced(Launcher.java:289)
        at org.codehaus.plexus.classworlds.launcher.Launcher.launch(Launcher.java:229)
        at org.codehaus.plexus.classworlds.launcher.Launcher.mainWithExitCode(Launcher.java:415)
        at org.codehaus.plexus.classworlds.launcher.Launcher.main(Launcher.java:356)
    [DEBUG] flushTransaction
    [DEBUG] ... calling @PreDestroy method: org.apache.isis.objectstore.jdo.datanucleus.service.support.TimestampService: close

这是提供者实体

    package domainapp.modules.provider.dom;

    //import domainapp.modules.provider.ProviderModule;
    import domainapp.modules.provider.ProviderModule.PropertyDomainEvent;

import javax.jdo.annotations.IdentityType;
import javax.jdo.annotations.VersionStrategy;
import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter;

import org.apache.isis.applib.annotation.Action;
import org.apache.isis.applib.annotation.Auditing;
import org.apache.isis.applib.annotation.CommandReification;
import org.apache.isis.applib.annotation.DomainObject;
import org.apache.isis.applib.annotation.Editing;
import org.apache.isis.applib.annotation.Parameter;
import org.apache.isis.applib.annotation.Property;
import org.apache.isis.applib.annotation.Publishing;
import org.apache.isis.applib.annotation.SemanticsOf;
import org.apache.isis.applib.annotation.Title;
import org.apache.isis.applib.services.i18n.TranslatableString;
import org.apache.isis.applib.services.message.MessageService;
import org.apache.isis.applib.services.repository.RepositoryService;
import org.apache.isis.applib.services.title.TitleService;
import org.apache.isis.applib.util.ObjectContracts;
import org.apache.isis.schema.utils.jaxbadapters.PersistentEntityAdapter;
import domainapp.modules.provider.dom.ProviderRepository;
//

import java.math.BigDecimal;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.Comparator;
import java.util.List;
import java.util.Set;
import java.util.SortedSet;
import java.util.TreeSet;

import javax.jdo.annotations.IdentityType;
import javax.jdo.annotations.VersionStrategy;
import javax.validation.constraints.Digits;
import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter;

import com.google.common.base.Objects;
import com.google.common.base.Predicate;
import com.google.common.collect.Ordering;

import org.joda.time.LocalDate;

import org.apache.isis.applib.Identifier;
import org.apache.isis.applib.NonRecoverableException;
import org.apache.isis.applib.RecoverableException;
import org.apache.isis.applib.annotation.Action;
import org.apache.isis.applib.annotation.Collection;
import org.apache.isis.applib.annotation.DomainObject;
import org.apache.isis.applib.annotation.Editing;
import org.apache.isis.applib.annotation.InvokeOn;
import org.apache.isis.applib.annotation.InvokedOn;
import org.apache.isis.applib.annotation.MemberOrder;
import org.apache.isis.applib.annotation.Optionality;
import org.apache.isis.applib.annotation.Parameter;
import org.apache.isis.applib.annotation.Programmatic;
import org.apache.isis.applib.annotation.Property;
import org.apache.isis.applib.annotation.Publishing;
import org.apache.isis.applib.annotation.RestrictTo;
import org.apache.isis.applib.annotation.SemanticsOf;
import org.apache.isis.applib.annotation.Where;
import org.apache.isis.applib.security.UserMemento;
import org.apache.isis.applib.services.actinvoc.ActionInvocationContext;
import org.apache.isis.applib.services.eventbus.EventBusService;
import org.apache.isis.applib.services.eventbus.ObjectCreatedEvent;
import org.apache.isis.applib.services.eventbus.ObjectLoadedEvent;
import org.apache.isis.applib.services.eventbus.ObjectPersistedEvent;
import org.apache.isis.applib.services.eventbus.ObjectPersistingEvent;
import org.apache.isis.applib.services.eventbus.ObjectRemovingEvent;
import org.apache.isis.applib.services.eventbus.ObjectUpdatedEvent;
import org.apache.isis.applib.services.eventbus.ObjectUpdatingEvent;
import org.apache.isis.applib.services.i18n.TranslatableString;
import org.apache.isis.applib.services.message.MessageService;
import org.apache.isis.applib.services.repository.RepositoryService;
import org.apache.isis.applib.services.scratchpad.Scratchpad;
import org.apache.isis.applib.services.title.TitleService;
import org.apache.isis.applib.services.user.UserService;
import org.apache.isis.applib.services.wrapper.HiddenException;
import org.apache.isis.applib.services.wrapper.WrapperFactory;
import org.apache.isis.applib.services.xactn.TransactionService;
import org.apache.isis.applib.util.ObjectContracts;
import org.apache.isis.applib.util.TitleBuffer;
import org.apache.isis.applib.value.Blob;
import org.apache.isis.applib.value.Clob;
import org.apache.isis.schema.utils.jaxbadapters.PersistentEntityAdapter;
//

import lombok.Builder;
import lombok.EqualsAndHashCode;
import lombok.Getter;
import lombok.Setter;
import lombok.ToString;
import org.apache.isis.applib.annotation.MemberOrder;
import org.apache.isis.applib.annotation.Optionality;
//import org.apache.isis.applib.services.eventbus.PropertyDomainEvent;
import org.apache.isis.applib.value.Blob;
import org.isisaddons.wicket.fullcalendar2.cpt.applib.CalendarEvent;
import org.isisaddons.wicket.fullcalendar2.cpt.applib.CalendarEventable;
import org.isisaddons.wicket.gmap3.cpt.applib.Locatable;
import org.isisaddons.wicket.gmap3.cpt.applib.Location;
import org.isisaddons.wicket.gmap3.cpt.service.LocationLookupService;
import domainapp.modules.provider.dom.ProviderMenu;
import domainapp.modules.provider.dom.ProviderRepository;

@javax.jdo.annotations.PersistenceCapable(
        identityType = IdentityType.DATASTORE,
        schema = "simple"
)
@javax.jdo.annotations.DatastoreIdentity(
        strategy = javax.jdo.annotations.IdGeneratorStrategy.IDENTITY,
        column = "id")
@javax.jdo.annotations.Version(
        strategy = VersionStrategy.DATE_TIME,
        column = "version")
@javax.jdo.annotations.Queries({
    @javax.jdo.annotations.Query(
            name = "findByName",
            value = "SELECT "
            + "FROM domainapp.modules.provider.dom.Provider  "
            + "WHERE name.indexOf(:name) >= 0 ")
})
@javax.jdo.annotations.Unique(name = "Provider_name_UNQ", members = {"name"})
@DomainObject(
        autoCompleteRepository = ProviderRepository.class, // for drop-downs, unless autoCompleteNXxx() or choicesNXxx() present
        autoCompleteAction = "autoComplete",
 //       updatedLifecycleEvent = ToDoItem.UpdatedEvent.class,
        auditing = Auditing.ENABLED
)
@XmlJavaTypeAdapter(PersistentEntityAdapter.class)
@EqualsAndHashCode(of = {"name"})
@ToString(of = {"name"})
public class Provider implements Comparable<Provider>, Locatable {

    /**
     *
     * The fields of the Provider entity name String required, website String,
     * twitter String, facebook String, email String, primaryLocation String,
     * country String, city String, state String, street String, apiKey String,
     * apiUser String, endpointUrl String, logo ImageBlob
     */
    @Builder
    public Provider(final String name) {
        setName(name);
    }

    @javax.jdo.annotations.Column(allowsNull = "false", length = 40)
    @Title(prepend = "Provider: ")
    @Property(editing = Editing.DISABLED)
    @Getter
    @Setter
    private String name;
//parent
    @javax.jdo.annotations.Column(allowsNull = "true")
    @Property(
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private Provider parent;    
//notes
    @javax.jdo.annotations.Column(allowsNull = "true", length = 4000)
    @Property(
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private String notes;

//website
    @javax.jdo.annotations.Column(allowsNull = "true", length = 40)
    @Property(
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private String website;
//facebook
    @javax.jdo.annotations.Column(allowsNull = "true", length = 40)
    @Property(
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private String facebook;
//twitter
    @javax.jdo.annotations.Column(allowsNull = "true", length = 40)
    @Property(
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private String twitter;
//instagram
    @javax.jdo.annotations.Column(allowsNull = "true", length = 40)
    @Property(
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private String instagram;
//email String,
    @javax.jdo.annotations.Column(allowsNull = "true", length = 40)
    @Property(
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private String email;
//  primaryLocation String, copy the way the location is done in todoApp, meaning we include 
//         locatable

    // public static class LocationDomainEvent extends ProviderModule.PropertyDomainEvent<Location> { }
    private Double locationLatitude;
    private Double locationLongitude;

    @Property(
            //ISIS-1138: Location value type not parsed from string, so fails to locate constructor
            //domainEvent = LocationDomainEvent.class,
            optionality = Optionality.OPTIONAL,
            //editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    public Location getLocation() {
        return locationLatitude != null && locationLongitude != null ? new Location(locationLatitude, locationLongitude) : null;
    }

    public void setLocation(final Location location) {
        locationLongitude = location != null ? location.getLongitude() : null;
        locationLatitude = location != null ? location.getLatitude() : null;
    }

    @MemberOrder(name = "location", sequence = "1")
    public Provider updateLocation(
            final String address) {
        final Location location = this.locationLookupService.lookup(address);
        setLocation(location);
        setAddress(address);
        return this;
    }

//  address String,
    @MemberOrder(name = "location", sequence = "2")
    @javax.jdo.annotations.Column(allowsNull = "true", length = 200)
    @Property(
            editing = Editing.DISABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private String address;
//  city String,
//  state String,
//    street String,
//  apiKey String,
    @javax.jdo.annotations.Column(allowsNull = "true", length = 40)
    @Property(
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private String apiKey;
//  apiUser String,
    @javax.jdo.annotations.Column(allowsNull = "true", length = 40)
    @Property(
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private String apiUser;
//  endpointUrl String,
    @javax.jdo.annotations.Column(allowsNull = "true", length = 40)
    @Property(
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private String endpointUrl;
//  logo ImageBlob  

    //     public static class LogoDomainEvent extends PropertyDomainEvent<Blob>  { }
    @javax.jdo.annotations.Persistent(defaultFetchGroup = "false", columns = {
        @javax.jdo.annotations.Column(name = "logo_name")
        ,
            @javax.jdo.annotations.Column(name = "logo_mimetype")
        ,
            @javax.jdo.annotations.Column(name = "logo_bytes", jdbcType = "BLOB", sqlType = "LONGVARBINARY")
    })
    @Property(
            //           domainEvent = LogoDomainEvent.class,
            optionality = Optionality.OPTIONAL,
            editing = Editing.ENABLED,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    @Getter
    @Setter
    private Blob logo;
//
//updatename

    @Action(
            semantics = SemanticsOf.IDEMPOTENT,
            command = CommandReification.ENABLED,
            publishing = Publishing.ENABLED
    )
    public Provider updateName(
            @Parameter(maxLength = 40)
            final String name) {
        setName(name);
        return this;
    }

    public String default0UpdateName() {
        return getName();
    }

    public TranslatableString validate0UpdateName(final String name) {
        return name != null && name.contains("!") ? TranslatableString.tr("Exclamation mark is not allowed") : null;
    }

    @Action(semantics = SemanticsOf.NON_IDEMPOTENT_ARE_YOU_SURE)
    public void delete() {
        final String title = titleService.titleOf(this);
        messageService.informUser(String.format("'%s' deleted", title));
        repositoryService.remove(this);
    }

    @Override
    public int compareTo(final Provider other) {
        return ObjectContracts.compare(this, other, "name");
    }

    @javax.inject.Inject
    RepositoryService repositoryService;

    @javax.inject.Inject
    TitleService titleService;

    @javax.inject.Inject
    MessageService messageService;

    @javax.inject.Inject
    private LocationLookupService locationLookupService;

    @javax.inject.Inject
    private ProviderMenu providerMenu;

    @javax.inject.Inject
    private ProviderRepository providerRepository;

}

这是 ProviderRepository

    package domainapp.modules.provider.dom;

import java.util.List;

import org.apache.isis.applib.annotation.DomainService;
import org.apache.isis.applib.annotation.NatureOfService;
import org.apache.isis.applib.annotation.Programmatic;
import org.apache.isis.applib.query.QueryDefault;
import org.apache.isis.applib.services.registry.ServiceRegistry2;
import org.apache.isis.applib.services.repository.RepositoryService;

@DomainService(
        nature = NatureOfService.DOMAIN,
        repositoryFor = Provider.class
)
public class ProviderRepository {

    public List<Provider> listAll() {
        return repositoryService.allInstances(Provider.class);
    }

    public List<Provider> findByName(final String name) {
        return repositoryService.allMatches(
                new QueryDefault<>(
                        Provider.class,
                        "findByName",
                        "name", name));
    }

    public Provider create(final String name) {
        final Provider object = new Provider(name);
        serviceRegistry.injectServicesInto(object);
        repositoryService.persist(object);
        return object;
    }
    //region > autoComplete (programmatic)
    @Programmatic // doesn't need to be part of metamodel
    public List<Provider> autoComplete(final String description) {
        return findByName(description);
    }
    //endregion
    @javax.inject.Inject
    RepositoryService repositoryService;
    @javax.inject.Inject
    ServiceRegistry2 serviceRegistry;
    }

我一直无法弄清楚问题是什么。

4

1 回答 1

1

这里发生的事情是您正在运行 Isis Maven 插件,并且它使用了一个 AppManifest(在 pom.xml 中定义)——我猜它——没有引用包含这些类的新模块。

我猜你可能为你的新模块克隆了模块简单。在这种情况下,您可以通过以下任一方式解决问题:

HTH丹

于 2017-10-07T14:26:17.083 回答