예제 #1
0
  @Transactional
  private void updateCapacity(long total, long avail) {
    PrimaryStorageCapacityVO cvo =
        dbf.getEntityManager()
            .find(PrimaryStorageCapacityVO.class, self.getUuid(), LockModeType.PESSIMISTIC_WRITE);
    DebugUtils.Assert(
        cvo != null,
        String.format("how can there is no PrimaryStorageCapacityVO[uuid:%s]", self.getUuid()));

    cvo.setTotalPhysicalCapacity(total);
    cvo.setAvailablePhysicalCapacity(avail);
    dbf.getEntityManager().merge(cvo);
  }
예제 #2
0
  protected PrimaryStorageVO updatePrimaryStorage(APIUpdatePrimaryStorageMsg msg) {
    boolean update = false;
    if (msg.getName() != null) {
      self.setName(msg.getName());
      update = true;
    }
    if (msg.getDescription() != null) {
      self.setDescription(msg.getDescription());
      update = true;
    }

    return update ? self : null;
  }
예제 #3
0
 @Transactional(readOnly = true)
 private void checkIfBackupStorageAttachedToMyZone(String bsUuid) {
   String sql =
       "select bs.uuid from BackupStorageVO bs, BackupStorageZoneRefVO ref where bs.uuid = ref.backupStorageUuid and ref.zoneUuid = :zoneUuid and bs.uuid = :bsUuid";
   TypedQuery<String> q = dbf.getEntityManager().createQuery(sql, String.class);
   q.setParameter("zoneUuid", self.getZoneUuid());
   q.setParameter("bsUuid", bsUuid);
   if (q.getResultList().isEmpty()) {
     throw new OperationFailureException(
         errf.stringToOperationError(
             String.format(
                 "backup storage[uuid:%s] is not attached to zone[uuid:%s] the primary storage[uuid:%s] belongs to",
                 bsUuid, self.getZoneUuid(), self.getUuid())));
   }
 }
예제 #4
0
  private void handle(final ConnectPrimaryStorageMsg msg) {
    final ConnectPrimaryStorageReply reply = new ConnectPrimaryStorageReply();
    self.setStatus(PrimaryStorageStatus.Connecting);
    self = dbf.updateAndRefresh(self);
    connectHook(
        msg,
        new Completion(msg) {
          @Override
          public void success() {
            self.setStatus(PrimaryStorageStatus.Connected);
            self = dbf.updateAndRefresh(self);
            reply.setConnected(true);
            logger.debug(
                String.format("successfully connected primary storage[uuid:%s]", self.getUuid()));
            bus.reply(msg, reply);
          }

          @Override
          public void fail(ErrorCode errorCode) {
            self.setStatus(PrimaryStorageStatus.Disconnected);
            self = dbf.updateAndRefresh(self);
            logger.debug(
                String.format(
                    "failed to connect primary storage[uuid:%s], %s", self.getUuid(), errorCode));
            reply.setConnected(false);
            bus.reply(msg, reply);
          }
        });
  }
예제 #5
0
 @Transactional
 private void handle(TakePrimaryStorageCapacityMsg msg) {
   PrimaryStorageCapacityVO vo =
       dbf.getEntityManager()
           .find(PrimaryStorageCapacityVO.class, self.getUuid(), LockModeType.PESSIMISTIC_WRITE);
   vo.setAvailableCapacity(vo.getAvailableCapacity() - msg.getSize());
   if (vo.getAvailableCapacity() < 0) {
     vo.setAvailableCapacity(0);
   }
   dbf.getEntityManager().merge(vo);
   TakePrimaryStorageCapacityReply reply = new TakePrimaryStorageCapacityReply();
   bus.reply(msg, reply);
 }
예제 #6
0
  @Transactional
  private void handle(PrimaryStorageReportCapacityMsg msg) {
    PrimaryStorageCapacityVO vo =
        dbf.getEntityManager()
            .find(PrimaryStorageCapacityVO.class, self.getUuid(), LockModeType.PESSIMISTIC_WRITE);
    if (vo.getTotalCapacity() == 0) {
      vo.setTotalCapacity(msg.getTotalCapacity());
      vo.setAvailableCapacity(msg.getAvailableCapacity());
      dbf.getEntityManager().merge(vo);
    }

    PrimaryStorageReportCapacityReply reply = new PrimaryStorageReportCapacityReply();
    bus.reply(msg, reply);
  }
예제 #7
0
  protected void handle(APIChangePrimaryStorageStateMsg msg) {
    APIChangePrimaryStorageStateEvent evt = new APIChangePrimaryStorageStateEvent(msg.getId());

    PrimaryStorageState currState = self.getState();
    PrimaryStorageStateEvent event = PrimaryStorageStateEvent.valueOf(msg.getStateEvent());
    PrimaryStorageState nextState = AbstractPrimaryStorage.getNextState(currState, event);

    try {
      extpEmitter.preChange(self, event);
    } catch (PrimaryStorageException e) {
      evt.setErrorCode(
          errf.instantiateErrorCode(SysErrors.CHANGE_RESOURCE_STATE_ERROR, e.getMessage()));
      bus.publish(evt);
      return;
    }

    extpEmitter.beforeChange(self, event);
    changeStateHook(event, nextState);
    self.setState(nextState);
    self = dbf.updateAndRefresh(self);
    extpEmitter.afterChange(self, event, currState);
    evt.setInventory(PrimaryStorageInventory.valueOf(self));
    bus.publish(evt);
  }
예제 #8
0
 protected String getSyncId() {
   return String.format("primaryStorage-%s", self.getUuid());
 }
예제 #9
0
  private void handle(final APISyncPrimaryStorageCapacityMsg msg) {
    final APISyncPrimaryStorageCapacityEvent evt =
        new APISyncPrimaryStorageCapacityEvent(msg.getId());

    FlowChain chain = FlowChainBuilder.newShareFlowChain();
    chain.setName(String.format("sync-capacity-of-primary-storage-%s", self.getUuid()));
    chain
        .then(
            new ShareFlow() {
              Long volumeUsage;
              Long snapshotUsage;
              Long totalPhysicalSize;
              Long availablePhysicalSize;

              @Override
              public void setup() {
                flow(
                    new NoRollbackFlow() {
                      String __name__ = "sync-capacity-used-by-volumes";

                      @Override
                      public void run(final FlowTrigger trigger, Map data) {
                        VolumeReportPrimaryStorageCapacityUsageMsg msg =
                            new VolumeReportPrimaryStorageCapacityUsageMsg();
                        msg.setPrimaryStorageUuid(self.getUuid());
                        bus.makeLocalServiceId(msg, VolumeConstant.SERVICE_ID);
                        bus.send(
                            msg,
                            new CloudBusCallBack(trigger) {
                              @Override
                              public void run(MessageReply reply) {
                                if (!reply.isSuccess()) {
                                  trigger.fail(reply.getError());
                                  return;
                                }

                                VolumeReportPrimaryStorageCapacityUsageReply r = reply.castReply();
                                volumeUsage = r.getUsedCapacity();
                                trigger.next();
                              }
                            });
                      }
                    });

                flow(
                    new NoRollbackFlow() {
                      String __name__ = "sync-capacity-used-by-volume-snapshots";

                      @Override
                      public void run(final FlowTrigger trigger, Map data) {
                        VolumeSnapshotReportPrimaryStorageCapacityUsageMsg msg =
                            new VolumeSnapshotReportPrimaryStorageCapacityUsageMsg();
                        msg.setPrimaryStorageUuid(self.getUuid());
                        bus.makeLocalServiceId(msg, VolumeSnapshotConstant.SERVICE_ID);
                        bus.send(
                            msg,
                            new CloudBusCallBack(trigger) {
                              @Override
                              public void run(MessageReply reply) {
                                if (!reply.isSuccess()) {
                                  trigger.fail(reply.getError());
                                  return;
                                }

                                VolumeSnapshotReportPrimaryStorageCapacityUsageReply r =
                                    reply.castReply();
                                snapshotUsage = r.getUsedSize();
                                trigger.next();
                              }
                            });
                      }
                    });

                flow(
                    new NoRollbackFlow() {
                      String __name__ = "sync-physical-capacity";

                      @Override
                      public void run(final FlowTrigger trigger, Map data) {
                        syncPhysicalCapacity(
                            new ReturnValueCompletion<PhysicalCapacityUsage>(trigger) {
                              @Override
                              public void success(PhysicalCapacityUsage returnValue) {
                                totalPhysicalSize = returnValue.totalPhysicalSize;
                                availablePhysicalSize = returnValue.availablePhysicalSize;
                                availablePhysicalSize =
                                    availablePhysicalSize < 0 ? 0 : availablePhysicalSize;
                                trigger.next();
                              }

                              @Override
                              public void fail(ErrorCode errorCode) {
                                trigger.fail(errorCode);
                              }
                            });
                      }
                    });

                done(
                    new FlowDoneHandler(msg) {
                      @Override
                      public void handle(Map data) {
                        writeToDb();
                        self = dbf.reload(self);
                        evt.setInventory(getSelfInventory());
                        bus.publish(evt);
                      }

                      @Transactional
                      private void writeToDb() {
                        PrimaryStorageCapacityVO vo =
                            dbf.getEntityManager()
                                .find(
                                    PrimaryStorageCapacityVO.class,
                                    self.getUuid(),
                                    LockModeType.PESSIMISTIC_WRITE);

                        long avail = vo.getTotalCapacity() - volumeUsage - snapshotUsage;
                        avail = avail < 0 ? 0 : avail;
                        vo.setAvailableCapacity(avail);
                        vo.setAvailablePhysicalCapacity(availablePhysicalSize);
                        vo.setTotalPhysicalCapacity(totalPhysicalSize);
                        dbf.getEntityManager().merge(vo);
                      }
                    });

                error(
                    new FlowErrorHandler(msg) {
                      @Override
                      public void handle(ErrorCode errCode, Map data) {
                        evt.setErrorCode(errCode);
                        bus.publish(evt);
                      }
                    });
              }
            })
        .start();
  }