Инициализация исключения локального хранилища данных: среда для этого потока не зарегистрирована - PullRequest
11 голосов
/ 23 марта 2011

Я хотел бы инициализировать свое локальное хранилище данных с некоторыми данными, используя обычная Java-программа (я не хочу запускать сервер разработки и вызвать сервис / сервлет), и я получаю следующее исключение

ИСКЛЮЧЕНИЕ:

Exception in thread "main" java.lang.NullPointerException: No API environment is registered for this thread. at com.google.appengine.api.datastore.DatastoreApiHelper.getCurrentAppId(DatastoreApiHelper.java:108) at com.google.appengine.api.datastore.DatastoreApiHelper.getCurrentAppIdNamespace(DatastoreApiHelper.java:118) at com.google.appengine.api.datastore.Key.(Key.java:104) at com.google.appengine.api.datastore.Key.(Key.java:88) at com.google.appengine.api.datastore.Key.(Key.java:84) at com.google.appengine.api.datastore.Entity.(Entity.java:122) at com.google.appengine.api.datastore.Entity.(Entity.java:103) at org.datanucleus.store.appengine.DatastoreFieldManager.(DatastoreFieldManager.java:187) at org.datanucleus.store.appengine.DatastorePersistenceHandler.insertPreProcess(DatastorePersistenceHandler.java:338) at org.datanucleus.store.appengine.DatastorePersistenceHandler.insertObjects(DatastorePersistenceHandler.java:251) at org.datanucleus.store.appengine.DatastorePersistenceHandler.insertObject(DatastorePersistenceHandler.java:240) at org.datanucleus.state.JDOStateManagerImpl.internalMakePersistent(JDOStateManagerImpl.java:3185) at org.datanucleus.state.JDOStateManagerImpl.makePersistent(JDOStateManagerImpl.java:3161) at org.datanucleus.ObjectManagerImpl.persistObjectInternal(ObjectManagerImpl.java:1298) at org.datanucleus.ObjectManagerImpl.persistObject(ObjectManagerImpl.java:1175) at org.datanucleus.jdo.JDOPersistenceManager.jdoMakePersistent(JDOPersistenceManager.java:669) at org.datanucleus.jdo.JDOPersistenceManager.makePersistent(JDOPersistenceManager.java:694) at com.stuff.server.GreetingServiceImpl.saveContact(GreetingServiceImpl.java:25) at com.stuff.server.TestCase.testServerCallBack(TestCase.java:18) at com.stuff.server.TestCase.main(TestCase.java:13)

TestCase.java

<pre> public class TestCase { static GreetingServiceImpl greetingServiceImpl = new GreetingServiceImpl();</p> <pre><code>public static void main(String[] args) { testServerCallBack();//line9 } private static void testServerCallBack() { Contacts contacts = new Contacts("this is", "awesome"); greetingServiceImpl.saveContact(contacts);//line:14 }

}

приветствие ..... impl.java

<pre> public class GreetingServiceImpl extends RemoteServiceServlet implements GreetingService {</p> <pre><code>public String greetServer(String input) throws IllegalArgumentException { return ""; } @Override public void saveContact(Contacts contacts) { PersistenceManager pm = PMF.get().getPersistenceManager(); pm.makePersistent(contacts); //line:20 pm.close(); }

}

Есть ли способ сделать это? Как?

Ответы [ 3 ]

8 голосов
/ 23 марта 2011

Google предоставляет вспомогательный класс, который делает именно то, что вам нужно - запускает достаточно кода для работы с базой данных, без запуска всего сервера dev. См. setUp и tearDown методы на http://code.google.com/appengine/docs/java/tools/localunittesting.html

3 голосов
/ 21 ноября 2015

Вам необходимо настроить тестовую службу хранилища данных для текущего потока. В основном вы можете сделать это:

private static void testServerCallBack() {
    LocalServiceTestHelper helper =
        new LocalServiceTestHelper(new LocalDatastoreServiceTestConfig());
    helper.setUp();
    Contacts contacts = new Contacts("this is", "awesome");
    greetingServiceImpl.saveContact(contacts);//line:14
}

Это инициализирует службу базы данных (подделка, только для тестирования) для только для этого метода .

или лучше вы можете сделать:

private final LocalServiceTestHelper helper =
  new LocalServiceTestHelper(new LocalDatastoreServiceTestConfig());

@Before
public void setUp() {
   helper.setUp();
}

@After
public void tearDown() {
   helper.tearDown();
}

Таким образом, служба баз данных будет работать со всеми методами тестирования.

Обратите внимание, что если вы используете разные потоки для доступа к БД, вы получите отдельную базу данных для каждого потока. Это не то, что вы хотите, скорее всего. Я имею в виду helper.setUp(), но не устанавливайте новую отдельную службу базы данных для текущего потока, и все данные, хранящиеся в этой базе данных, будут доступны только из текущего потока.

Подробнее см .: http://code.google.com/appengine/docs/java/tools/localunittesting.html

2 голосов
/ 14 декабря 2012

Просто добавьте эти 3 библиотеки (приложение к тестовой) к вашему classpath:

${SDK_ROOT}/lib/impl/appengine-api.jar
${SDK_ROOT}/lib/impl/appengine-api-labs.jar
${SDK_ROOT}/lib/impl/appengine-api-stubs.jar

Это должно решить проблему.

...