2016-10-20 9 views
2

У меня проблема с базой данных neo4j. Когда я пытаюсь инициализировать данные, он должен просто создать один пример данных, но иногда, когда я пытаюсь инициализировать данные, он создает данные с двойной выборкой. Во второй раз нет никаких следов вызова. Это Config моей Neo4jNeo4j 3.0.6 и neo4j-ogm 2.0.5 - Создание дубликатов данных в базе данных

@Configuration 
@EnableNeo4jRepositories(basePackages = "com.example.neo.repository") 
@EnableTransactionManagement 
public class Neo4jConfig extends Neo4jConfiguration { 
    @Override 
    @Bean 
    public SessionFactory getSessionFactory() { 
     // with domain entity base package(s) 
     return new SessionFactory("com.example.neo.model", "BOOT-INF.classes.com.example.neo.model"); 
    } 

    // needed for session in view in web-applications 
    @Override 
    @Bean 
    @Scope(value = "session", proxyMode = ScopedProxyMode.TARGET_CLASS) 
    public Session getSession() throws Exception { 
     return super.getSession(); 
    } 
} 

Это, как я назвал свою функцию

@RequestMapping(value = "/initCurrency") 
public ModelAndView initCurrency() { 
    initializationService.initCurrency(); 

    ModelAndView model = new ModelAndView("redirect:/"); 
    return model; 
} 

Это функция initializationService

private String[][] currencyList = { 
     { "USD", "7.5" }, 
     { "DKK", "1" }, 
     { "AFN", "1"},{ "EUR", "1"},{ "ALL", "1"},{ "DZD", "1"},{ "USD", "1"},{ "AOA", "1"},{ "XCD", "1"}, 
     { "ARS", "1"},{ "AMD", "1"},{ "AWG", "1"},{ "SHP", "1"},{ "AUD", "1"},{ "AZN", "1"},{ "BSD", "1"}, 
     { "BHD", "1"},{ "BDT", "1"},{ "BBD", "1"} 
} 
@Override 
public void initCurrency() { 
    for (String[] currency : currencyList) { 
     Currency existCurrency = currencyService.findByName(currency[0]); 

     if (existCurrency == null) { 
      existCurrency = new Currency(currency[0], Double.valueOf(currency[1])); 
      currencyService.save(existCurrency); 
     } 
    } 
} 
+1

Возможно, вы должны добавить ограничение уникальности в код валюты - как предотвратить дубликаты, так и пролить свет на то, что происходит не так. –

+0

@JasperBlues Я уже добавляю уникальный идентификатор и предотвращаю дублирование с помощью findByName. Если существует CUrrency, его следует пропустить код сохранения. Но когда я проверяю базу данных neo4j, есть двойные данные с уникальным идентификатором differnt. –

+1

Что означает Jasper, вы должны сделать уникальное имя валюты, используя что-то вроде 'CREATE CONSTRAINT ON (n: Currency) ASSERT n.name IS UNIQUE' (предположим, что' USD' переходит в свойство 'name'' Currency 'label). Приложение не сможет создать 2 узла с одинаковым именем валюты, второй - сбой, и вы найдете исключение в своих журналах. –

ответ

2

Единственный надежный способ избежать дубликатов, чтобы иметь фактический unicity constraint на имущество:

CREATE CONSTRAINT ON (n:Currency) ASSERT n.name IS UNIQUE; 

В SDN 4 нет способа [0-2] (пока) создать такое ограничение из модели (в SDN 3.x было добавлено примечание или @Indexed(unique = true)), поэтому вам нужно будет запустить независимо (например, используя Liquigraph!).

Делая поиск, чтобы охранять создание не достаточно в параллельной среде (последовательные вызовы OK), потому что нет блокировки между чтением и записью, которые могут привести к следующему сценарию с чередованием исполнения:

  • Поток а проверяет существование, не найти узел
  • Thread B проверяет существование, не находит узел либо
  • Поток а создает узел валюты под названием «USB»
  • Thread B создает другой валютный узел с s AME имя

Так как вы в конечном итоге с дубликатами, 2 одновременных вызовов происходят. Балансировщик нагрузки с очень коротким таймаутом и настроен на повторную попытку? Активируйте журналы HTTP, добавьте некоторые записи в контроллер Spring или службу, запишите трафик с помощью tcpdump и т. Д. Будет легче изолировать второй вызов, как только ограничение unicity будет активным, так как вы получите исключение.

+0

Да. Это связано с тем, что два потока выполняются одновременно, поэтому он создает дубликаты данных. Это похоже на ваше объяснение. ANyway Спасибо за эту информацию, очень полезно. –

+1

Стоит упомянуть, что в OGM '2.1.0-SNAPSHOT' поддерживаются' @ Index' и '@Index (unique = true)': https://github.com/neo4j/neo4j-ogm/pull/243 – digx1

 Смежные вопросы

  • Нет связанных вопросов^_^