Spring Data Neo4j坚持丰富的关系

时间:2013-07-09 08:43:31

标签: java neo4j spring-data-neo4j

我遇到了一个明显相当常见的问题,并且想知道我在这里做错了什么。

我有两个类型为“帐户”的节点,并希望在它们之间添加“FRIEND”关系。但我不会简单地在对应帐户能够接受或拒绝友谊请求(通常流程)之前添加关系。所以我创建了一个名为“友谊”的丰富关系。

我的单元测试显示请求将添加到对应帐户,但不会添加到启动器帐户。

以下是我目前使用的代码的摘录:

   @Fetch
   @RelatedToVia(type =  "FRIEND", direction = Direction.BOTH)
   private Set<Friendship> friends;
   ...
   ... 
   public void addFriendshipRequest(Friendship friendship) {
      this.friends.add(friendship);
   }

   public Set<Friendship> getConfirmedFriends() {
    Set<Friendship> friendships = new HashSet<Friendship>();
    for(Friendship f : this.friends) {
        if(f.getState() == Friendship.State.CONFIRMED) {
            friendships.add(f);
        }
    }
    return friendships;
}

public Set<Friendship> getFriendships() {
    return this.friends;
}

public Set<Friendship> getFriendRequests() {
    Set<Friendship> requests = new HashSet<Friendship>();
    for(Friendship f : this.friends) {
        if(f.getState() == Friendship.State.REQUESTED) {
            requests.add(f);
        }
    }
    return requests;
} 
...
...
}

@Fetch @RelatedToVia(type = "FRIEND", direction = Direction.BOTH) private Set<Friendship> friends; ... ... public void addFriendshipRequest(Friendship friendship) { this.friends.add(friendship); } public Set<Friendship> getConfirmedFriends() { Set<Friendship> friendships = new HashSet<Friendship>(); for(Friendship f : this.friends) { if(f.getState() == Friendship.State.CONFIRMED) { friendships.add(f); } } return friendships; } public Set<Friendship> getFriendships() { return this.friends; } public Set<Friendship> getFriendRequests() { Set<Friendship> requests = new HashSet<Friendship>(); for(Friendship f : this.friends) { if(f.getState() == Friendship.State.REQUESTED) { requests.add(f); } } return requests; } ... ... }

现在是我的“友谊”关系实体

相应的服务

import org.springframework.data.neo4j.annotation.EndNode;
import org.springframework.data.neo4j.annotation.GraphId;
import org.springframework.data.neo4j.annotation.RelationshipEntity;
import org.springframework.data.neo4j.annotation.StartNode;
import java.io.Serializable;
import java.util.Date;

@RelationshipEntity(type = "FRIEND")
public class Friendship implements Serializable {

public enum State { REQUESTED, CONFIRMED }

@GraphId
private Long id;

@StartNode
private Account requester;

@EndNode
private Account confirmer;

private State state;

private Date dateOfRequest;

private Date dateOfConfirmation;

public Friendship(Account requester, Account target) {
    this.state = State.REQUESTED;
    this.confirmer = target;
    this.requester = requester;
    this.dateOfRequest = new Date();
}

public Friendship() { }

... getter/setter and stuff ommitted


}

我的简单单元测试检查一切是否顺利......

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.neo4j.support.Neo4jTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Date;

import static org.springframework.util.Assert.notNull;

@Service("friendshipService")
@Transactional
@SuppressWarnings("SpringJavaAutowiringInspection")
public class FriendshipServiceImpl implements FriendshipService {

@Autowired
private Neo4jTemplate template;

/**
 * request a friendship with another account
 *
 * @param requester
 * @param target
 */
@Override
public void requestFriendship(Account requester, Account target) {
    notNull(target);
    if(!target.hasFriendshipWith(requester.getId())) {
        target.addFriendshipRequest(new Friendship(requester, target));
        template.save(target);
    }
}

/**
 * change pending state of friendship request to CONFIRMED
 *
 * @param confirmer
 * @param requester
 */
@Override
public void acceptFriendshipRequest(Account confirmer, Account requester) {
    notNull(confirmer);
    for(Friendship f : confirmer.getFriendRequests()) {
        if (f.getRequester().equals(requester)) {
            f.setState(Friendship.State.CONFIRMED);
            f.setDateOfConfirmation(new Date());
        }
    }
    template.save(confirmer);
}

/**
 * declines friendship request by removing it
 *
 * @param confirmer
 * @param requester
 */
@Override
public void declineFriendshipRequest(Account confirmer, Account requester) {
    notNull(confirmer);
    for(Friendship f : confirmer.getFriendRequests()) {
        if (f.getRequester().equals(requester)) {
            confirmer.getFriendships().remove(f);
        }
    }
    template.save(confirmer);
}

}

所以,现在,当我打电话给friendshipService.requestFriendship(我自己,友好的汉斯)时,我认为两个账户之间的关系将会建立,当我指出两个方向时,我进一步假设,当我检查对方友情时列表,也会与第一个帐户有关系。不幸的是,这个(assertThat(我的.getFriendships()。size(),是(1));)因为集合为空而失败。

你能指出我在这里做错了什么吗?我在最近几天尝试过 - 不幸的是没有成功。也许这只是一件小事。但我找不到它。

哦,我正在使用的版本号是

  • Spring Data Neo4j 2.1.0.RELEASE
  • Spring Core 3.2.0.RELEASE
  • Neo4j 1.8.1

非常感谢提前。

1 个答案:

答案 0 :(得分:0)

您必须从数据库中读回我自己的对象才能更新关系字段,否则您只是在创建新关系之前使用您已阅读的对象。