@SuppressWarnings("deprecation")
 private TransactionOptions createDatastoreTransactionOptionsPrototype(
     PersistenceConfiguration persistenceConfig) {
   //    return TransactionOptions.Builder.withXG(
   return TransactionOptions.Builder.allowMultipleEntityGroups(
       persistenceConfig.getBooleanProperty(DATASTORE_ENABLE_XG_TXNS_PROPERTY));
 }
  @Test
  public void crossGroupTransactions() {

    TransactionOptions transactionOptions = TransactionOptions.Builder.withXG(true);
    Transaction transaction = datastore.beginTransaction(transactionOptions);

    Entity a = new Entity("A");
    datastore.put(a);

    Entity b = new Entity("B", a.getKey());
    datastore.put(b);

    Entity c = new Entity("C", a.getKey());
    datastore.put(c);

    Entity d = new Entity("D");
    datastore.put(d);

    Entity e = new Entity("E");
    datastore.put(e);

    Entity f = new Entity("F");
    datastore.put(f);

    Entity z = new Entity("Z");
    datastore.put(z);

    transaction.commit();
  }
 // visible for testing
 static TransactionOptions copyTransactionOptions(TransactionOptions txnOpts) {
   // Maintenance nightmare, use clone() once it's available in the sdk
   TransactionOptions options = TransactionOptions.Builder.withDefaults();
   if (txnOpts.isXG()) {
     options.setXG(txnOpts.isXG());
   } else {
     options.clearXG();
   }
   return txnOpts;
 }
  @Override
  protected void doPost(HttpServletRequest req, HttpServletResponse resp)
      throws ServletException, IOException {

    UserPermissionsBean userPermissionsBean =
        (UserPermissionsBean) req.getAttribute(AuthRequestAttribute.USER_PERMISSIONS.getName());

    if (userPermissionsBean.getViewSessions() && userPermissionsBean.getViewSessionPermissions()) {

      if (userPermissionsBean.getChangeSessionPermissions()) {
        long sessionPermissionsCode = 0;
        if (req.getParameter(HtmlVariable.VIEW_SESSIONS.getName()) != null)
          sessionPermissionsCode =
              sessionPermissionsCode + SessionPermissions.VIEW_SESSIONS.getCode();
        if (req.getParameter(HtmlVariable.DISCONNECT_SESSIONS.getName()) != null)
          sessionPermissionsCode =
              sessionPermissionsCode + SessionPermissions.DISCONNECT_SESSIONS.getCode();
        if (req.getParameter(HtmlVariable.VIEW_SESSION_PERMISSIONS.getName()) != null)
          sessionPermissionsCode =
              sessionPermissionsCode + SessionPermissions.VIEW_SESSION_PERMISSIONS.getCode();
        if (req.getParameter(HtmlVariable.CHANGE_SESSION_PERMISSIONS.getName()) != null)
          sessionPermissionsCode =
              sessionPermissionsCode + SessionPermissions.CHANGE_SESSION_PERMISSIONS.getCode();

        Error error = Error.NONE;
        UserBean userBean = (UserBean) req.getAttribute(AuthRequestAttribute.USER.getName());
        DatastoreService datastore = DatastoreServiceFactory.getDatastoreService();
        Transaction txn = datastore.beginTransaction(TransactionOptions.Builder.withXG(true));
        User user = UserFactory.getByKey(datastore, txn, userBean.getKey());
        UserPermissions userPermissions = null;
        if (user == null) error = Error.NON_EXISTENT_USER;
        else if ((userPermissions =
                PermissionsFactory.getUserPermissionsByUserId(datastore, txn, user.getUserId()))
            == null) error = Error.NO_PERMISSIONS;
        else
          try {
            userPermissions.setSessionPermissions(sessionPermissionsCode);
            PermissionsFactory.updateUserPermissions(datastore, txn, userPermissions);
            txn.commit();
            userPermissionsBean = new UserPermissionsBean(userPermissions);
            req.setAttribute(AuthRequestAttribute.USER_PERMISSIONS.getName(), userPermissionsBean);
          } catch (ConcurrentModificationException e) {
            error = Error.ERROR_IN_SESSION_PERMISSIONS;
          }

        if (error != Error.NONE && txn.isActive()) txn.rollback();

        if (userPermissionsBean.getViewSessions()
            && userPermissionsBean.getViewSessionPermissions()) {
          req.setAttribute(HtmlVariable.ERROR.getName(), error.toString());
          req.getRequestDispatcher("/WEB-INF/auth/session-permissions.jsp").forward(req, resp);
        } else resp.sendRedirect("/auth/settings");
      } else req.getRequestDispatcher("/WEB-INF/auth/session-permissions.jsp").forward(req, resp);
    } else resp.sendRedirect("/auth/settings");
  }
  @Override
  public boolean createOrUpdateSparePart(
      String electronicShopID,
      String sparePartID,
      String name,
      String sparePartGroupID,
      String description,
      double deliveryPrice,
      String measuringUnit) {

    boolean flagNew = false;

    // check if we know that shop
    if (!ConfigurationProperties.getElectronicShopID().equals(electronicShopID)) {
      logger.warning("electronicShopID \"" + electronicShopID + "\" not known!");
      return false;
    }

    List<SparePart> spl = SparePart.queryGetByForeignID(sparePartID, 0, 1);
    SparePart sp;
    if (spl.size() == 0) {
      sp = new SparePart();
      flagNew = true;
    } else {
      sp = spl.get(0);
    }
    try {
      List<SparePartGroup> sparePartGroup =
          SparePartGroup.queryGetByForeignID(sparePartGroupID, 0, 1);
      if (sparePartGroup.size() == 0) {
        logger.warning("sparePartGroupID \"" + sparePartGroupID + "\" not known!");
        return false;
      }

      sp.setForeignID(sparePartID);
      sp.setSparePartGroupID(sparePartGroup.get(0).getID());
      sp.setName(name);
      sp.setDescription(description);
      sp.setDeliveryPrice(deliveryPrice);
      sp.setSalePrice(deliveryPrice); // <--- отначало продажната цена е същата като доставната !!!
      sp.setMeasuringUnit(measuringUnit);

      Transaction tr =
          DatastoreServiceFactory.getDatastoreService()
              .beginTransaction(TransactionOptions.Builder.withXG(true));
      sp.writeToDB();

      if (flagNew) {
        // добавяме нова част -> инициализираме записите за тази част във всички автосервизи
        SparePartAutoservice spa = new SparePartAutoservice();
        spa.setQuantityAvailable(0);
        spa.setQuantityBad(0);
        spa.setQuantityMinimum(0);
        spa.setQuantityOrdered(0);
        spa.setQuantityReserved(0);
        spa.setQuantityRequested(0);
        spa.setSparePartID(sp.getID());

        List<Autoservice> al = Autoservice.queryGetAll(0, 1000);
        for (Autoservice autoservice : al) {
          spa.setAutoserviceID(autoservice.getID());
          spa.writeToDB(true);
        }
      }

      tr.commit();

    } catch (RuntimeException e) {
      logger.log(Level.WARNING, "Can't write to DB!", e);
      return false;
    }

    return true;
  }