def buildMirrors(self, actionName, gpEnv, gpArray): """ Build the mirrors. gpArray must have already been altered to have updated directories -- that is, the failoverSegments from the mirrorsToBuild must be present in gpArray. """ testOutput("building %s segment(s)" % len(self.__mirrorsToBuild)) if len(self.__mirrorsToBuild) == 0: logger.info("No segments to " + actionName) return self.checkForPortAndDirectoryConflicts(gpArray) logger.info("%s segment(s) to %s" % (len(self.__mirrorsToBuild), actionName)) self.__verifyGpArrayContents(gpArray) # make sure the target directories are up-to-date # by cleaning them, if needed, and then copying a basic directory there # the postgresql.conf in that basic directory will need updating (to change the port) toStopDirectives = [] toEnsureMarkedDown = [] cleanupDirectives = [] copyDirectives = [] for toRecover in self.__mirrorsToBuild: if toRecover.getFailedSegment() is not None: # will stop the failed segment. Note that we do this even if we are recovering to a different location! toStopDirectives.append( GpStopSegmentDirectoryDirective( toRecover.getFailedSegment())) if toRecover.getFailedSegment().getSegmentStatus( ) == gparray.STATUS_UP: toEnsureMarkedDown.append(toRecover.getFailedSegment()) if toRecover.isFullSynchronization(): isTargetReusedLocation = False if toRecover.getFailedSegment() is not None and \ toRecover.getFailoverSegment() is None: # # We are recovering a failed segment in-place # cleanupDirectives.append( GpCleanupSegmentDirectoryDirective( toRecover.getFailedSegment())) isTargetReusedLocation = True if toRecover.getFailoverSegment() is not None: targetSegment = toRecover.getFailoverSegment() else: targetSegment = toRecover.getFailedSegment() d = GpCopySegmentDirectoryDirective(toRecover.getLiveSegment(), targetSegment, isTargetReusedLocation) copyDirectives.append(d) self.__ensureStopped(gpEnv, toStopDirectives) self.__ensureMarkedDown(gpEnv, toEnsureMarkedDown) self.__cleanUpSegmentDirectories(cleanupDirectives) self.__copySegmentDirectories(gpEnv, gpArray, copyDirectives) #Move the filespace for transaction and temporary files for toRecover in self.__mirrorsToBuild: target_segment = None if toRecover.getFailoverSegment() is not None: target_segment = toRecover.getFailoverSegment() elif toRecover.isFullSynchronization(): target_segment = toRecover.getFailedSegment() if target_segment is not None: self.__moveFilespaces(gpArray, target_segment) #If we are adding mirrors, we need to update the flat files on the primaries as well if actionName == "add": try: UpdateFlatFiles(gpArray, primaries=True).run() except MoveFilespaceError, e: logger.error(str(e)) raise
target_segment = toRecover.getFailedSegment() if target_segment is not None: self.__moveFilespaces(gpArray, target_segment) #If we are adding mirrors, we need to update the flat files on the primaries as well if actionName == "add": try: UpdateFlatFiles(gpArray, primaries=True).run() except MoveFilespaceError, e: logger.error(str(e)) raise else: try: print 'updating flat files' UpdateFlatFiles(gpArray, primaries=False).run() except MoveFilespaceError, e: logger.error(str(e)) raise # update and save metadata in memory for toRecover in self.__mirrorsToBuild: if toRecover.getFailoverSegment() is None: # we are recovering the lost segment in place seg = toRecover.getFailedSegment() else: seg = toRecover.getFailedSegment() # no need to update the failed segment's information -- it is # being overwritten in the configuration with the failover segment for gpArraySegment in gpArray.getDbList():