function __construct($controller, $name, $sourceClass, $fieldList, $detailFormFields = null, $sourceFilter = "", $sourceSort = "", $sourceJoin = "")
 {
     parent::__construct($controller, $name, $sourceClass, $fieldList, $detailFormFields, $sourceFilter, $sourceSort, $sourceJoin);
     $classes = array_reverse(ClassInfo::ancestry($this->controllerClass()));
     foreach ($classes as $class) {
         $singleton = singleton($class);
         $manyManyRelations = $singleton->uninherited('many_many', true);
         if (isset($manyManyRelations) && array_key_exists($this->name, $manyManyRelations)) {
             $this->manyManyParentClass = $class;
             $manyManyTable = $class . '_' . $this->name;
             break;
         }
         $belongsManyManyRelations = $singleton->uninherited('belongs_many_many', true);
         if (isset($belongsManyManyRelations) && array_key_exists($this->name, $belongsManyManyRelations)) {
             $this->manyManyParentClass = $class;
             $manyManyTable = $belongsManyManyRelations[$this->name] . '_' . $this->name;
             break;
         }
     }
     $tableClasses = ClassInfo::dataClassesFor($this->sourceClass);
     $source = array_shift($tableClasses);
     $sourceField = $this->sourceClass;
     if ($this->manyManyParentClass == $sourceField) {
         $sourceField = 'Child';
     }
     $parentID = $this->controller->ID;
     $this->sourceJoin .= " LEFT JOIN `{$manyManyTable}` ON (`{$source}`.`ID` = `{$sourceField}ID` AND `{$this->manyManyParentClass}ID` = '{$parentID}')";
     $this->joinField = 'Checked';
 }
 /**
  * Most of the code below was copied from ManyManyComplexTableField.
  * Painful, but necessary, until PHP supports multiple inheritance.
  */
 function __construct($controller, $name, $sourceClass, $fieldList, $detailFormFields = null, $sourceFilter = "", $sourceSort = "Created DESC", $sourceJoin = "")
 {
     parent::__construct($controller, $name, $sourceClass, $fieldList, $detailFormFields, $sourceFilter, $sourceSort, $sourceJoin);
     $manyManyTable = false;
     $classes = array_reverse(ClassInfo::ancestry($this->controllerClass()));
     foreach ($classes as $class) {
         if ($class != "Object") {
             $singleton = singleton($class);
             $manyManyRelations = $singleton->uninherited('many_many', true);
             if (isset($manyManyRelations) && array_key_exists($this->name, $manyManyRelations)) {
                 $this->manyManyParentClass = $class;
                 $manyManyTable = $class . '_' . $this->name;
                 break;
             }
             $belongsManyManyRelations = $singleton->uninherited('belongs_many_many', true);
             if (isset($belongsManyManyRelations) && array_key_exists($this->name, $belongsManyManyRelations)) {
                 $this->manyManyParentClass = $class;
                 $manyManyTable = $belongsManyManyRelations[$this->name] . '_' . $this->name;
                 break;
             }
         }
     }
     if (!$manyManyTable) {
         user_error("I could not find the relation {$this}-name in " . $this->controllerClass() . " or any of its ancestors.", E_USER_WARNING);
     }
     $tableClasses = ClassInfo::dataClassesFor($this->sourceClass);
     $source = array_shift($tableClasses);
     $sourceField = $this->sourceClass;
     if ($this->manyManyParentClass == $sourceField) {
         $sourceField = 'Child';
     }
     $parentID = $this->controller->ID;
     $this->sourceJoin .= " LEFT JOIN `{$manyManyTable}` ON (`{$source}`.`ID` = `{$sourceField}ID` AND `{$this->manyManyParentClass}ID` = '{$parentID}')";
     $this->joinField = 'Checked';
 }
 /**
  * Modified version of the SiteTree publish method.
  *
  * @return <type>
  */
 public function doPublish()
 {
     if (!$this->owner->canPublish()) {
         return false;
     }
     $class = $this->owner->class;
     $ownerId = $this->owner->ID;
     $dataClasses = ClassInfo::dataClassesFor($class);
     $dataClasses = array_values($dataClasses);
     $class = $dataClasses[count($dataClasses) - 1];
     $original = Versioned::get_one_by_stage("{$class}", "Live", "\"{$class}\".\"ID\" = {$ownerId}");
     if (!$original) {
         $original = new $class();
     }
     $this->owner->invokeWithExtensions('onBeforePublish', $original);
     // Handle activities undertaken by decorators
     $this->owner->Status = "Published";
     //$this->PublishedByID = Member::currentUser()->ID;
     $this->owner->write();
     $this->owner->publish("Stage", "Live");
     if ($this->owner->hasField('Sort')) {
         // find the table that actually defines the sortable field
         $class = get_class($this->owner);
         if ($this->owner->hasMethod('findClassDefiningSortField')) {
             $class = $this->owner->findClassDefiningSortField();
         }
         DB::query("UPDATE \"{$class}_Live\"\n\t\t\t\tSET \"Sort\" = (SELECT \"{$class}\".\"Sort\" FROM \"{$class}\" WHERE \"{$class}_Live\".\"ID\" = \"{$class}\".\"ID\")");
     }
     // Handle activities undertaken by decorators
     $this->owner->invokeWithExtensions('onAfterPublish', $original);
     return true;
 }
Ejemplo n.º 4
0
	function __construct($controller, $name, $sourceClass, $fieldList = null, $detailFormFields = null, $sourceFilter = "", $sourceSort = "", $sourceJoin = "") {

		Deprecation::notice('3.0', 'Use GridField with GridFieldConfig_RelationEditor');

		parent::__construct($controller, $name, $sourceClass, $fieldList, $detailFormFields, $sourceFilter, $sourceSort, $sourceJoin);
		
		$classes = array_reverse(ClassInfo::ancestry($this->controllerClass()));
		foreach($classes as $class) {
			$singleton = singleton($class);
			$manyManyRelations = $singleton->uninherited('many_many', true);
			if(isset($manyManyRelations) && array_key_exists($this->name, $manyManyRelations)) {
				$this->manyManyParentClass = $class;
				$manyManyTable = $class . '_' . $this->name;
				break;
			}
			$belongsManyManyRelations = $singleton->uninherited( 'belongs_many_many', true );
			 if( isset( $belongsManyManyRelations ) && array_key_exists( $this->name, $belongsManyManyRelations ) ) {
				$this->manyManyParentClass = $class;
				$manyManyTable = $belongsManyManyRelations[$this->name] . '_' . $this->name;
				break;
			}
		}
		$tableClasses = ClassInfo::dataClassesFor($this->sourceClass);
		$source = array_shift($tableClasses);
		$sourceField = $this->sourceClass;
		if($this->manyManyParentClass == $sourceField)
			$sourceField = 'Child';
		$parentID = $this->controller->ID;
		
		$this->sourceJoin .= " LEFT JOIN \"$manyManyTable\" ON (\"$source\".\"ID\" = \"$manyManyTable\".\"{$sourceField}ID\" AND \"{$this->manyManyParentClass}ID\" = '$parentID')";
		
		$this->joinField = 'Checked';
	}
 function __construct($controller, $name, $sourceClass, $fieldList = null, $detailFormFields = null, $sourceFilter = "", $sourceSort = "", $sourceJoin = "")
 {
     parent::__construct($controller, $name, $sourceClass, $fieldList, $detailFormFields, $sourceFilter, $sourceSort, $sourceJoin);
     //Sort by heirarchy, depending on number of parents indent
     $classes = array_reverse(ClassInfo::ancestry($this->controllerClass()));
     foreach ($classes as $class) {
         $singleton = singleton($class);
         $manyManyRelations = $singleton->uninherited('many_many', true);
         if (isset($manyManyRelations) && array_key_exists($this->name, $manyManyRelations)) {
             $this->manyManyParentClass = $class;
             $this->manyManyTable = $class . '_' . $this->name;
             break;
         }
         $belongsManyManyRelations = $singleton->uninherited('belongs_many_many', true);
         if (isset($belongsManyManyRelations) && array_key_exists($this->name, $belongsManyManyRelations)) {
             $singleton = singleton($belongsManyManyRelations[$this->name]);
             $manyManyRelations = $singleton->uninherited('many_many', true);
             $this->manyManyParentClass = $class;
             $relation = array_flip($manyManyRelations);
             $this->manyManyTable = $belongsManyManyRelations[$this->name] . '_' . $relation[$class];
             break;
         }
     }
     $tableClasses = ClassInfo::dataClassesFor($this->sourceClass);
     $source = array_shift($tableClasses);
     $sourceField = $this->sourceClass;
     if ($this->manyManyParentClass == $sourceField) {
         $sourceField = 'Child';
     }
     $parentID = $this->controller->ID;
     $this->sourceJoin .= " LEFT JOIN \"{$this->manyManyTable}\" ON (\"{$source}\".\"ID\" = \"{$this->manyManyTable}\".\"{$sourceField}ID\" AND \"{$this->manyManyTable}\".\"{$this->manyManyParentClass}ID\" = '{$parentID}')";
     $this->joinField = 'Checked';
 }
 /**
  * @covers ClassInfo::dataClassesFor()
  */
 public function testDataClassesFor()
 {
     $expect = array('ClassInfoTest_BaseDataClass' => 'ClassInfoTest_BaseDataClass', 'ClassInfoTest_HasFields' => 'ClassInfoTest_HasFields');
     $classes = array('ClassInfoTest_BaseDataClass', 'ClassInfoTest_NoFields', 'ClassInfoTest_HasFields');
     foreach ($classes as $class) {
         $this->assertEquals($expect, ClassInfo::dataClassesFor($class));
     }
 }
Ejemplo n.º 7
0
 /**
  * Assign a sort number when object is written
  * @see DataExtension::onBeforeWrite()
  */
 public function onBeforeWrite()
 {
     if (!$this->owner->ID && !$this->owner->SortOrder || !$this->owner->SortOrder) {
         $classes = ClassInfo::dataClassesFor($this->owner->ClassName);
         $sql = new SQLQuery('count(ID)', array_shift($classes));
         $val = $sql->execute()->value();
         $this->owner->SortOrder = is_numeric($val) ? $val + 1 : 1;
     }
 }
 /**
  * Assign a sort number when object is written
  * @see DataExtension::onBeforeWrite()
  */
 public function onBeforeWrite()
 {
     if (!$this->owner->exists() || !$this->owner->SortOrder) {
         $classes = ClassInfo::dataClassesFor($this->owner->ClassName);
         $sql = new SQLQuery('MAX("SortOrder")', '"' . array_shift($classes) . '"');
         $val = $sql->execute()->value();
         $this->owner->SortOrder = is_numeric($val) ? $val + 1 : 1;
     }
 }
 public static function allFieldsForClass($class)
 {
     $dataClasses = ClassInfo::dataClassesFor($class);
     $fields = array();
     foreach ($dataClasses as $dataClass) {
         $fields = array_merge($fields, array_keys(DataObject::database_fields($dataClass)));
     }
     return array_combine($fields, $fields);
 }
 /**
  * @covers ClassInfo::dataClassesFor()
  */
 public function testDataClassesFor()
 {
     $expect = array('ClassInfoTest_BaseDataClass' => 'ClassInfoTest_BaseDataClass', 'ClassInfoTest_HasFields' => 'ClassInfoTest_HasFields', 'ClassInfoTest_WithRelation' => 'ClassInfoTest_WithRelation');
     $classes = array('ClassInfoTest_BaseDataClass', 'ClassInfoTest_NoFields', 'ClassInfoTest_HasFields');
     $this->assertEquals($expect, ClassInfo::dataClassesFor($classes[0]));
     $this->assertEquals($expect, ClassInfo::dataClassesFor($classes[1]));
     $expect = array('ClassInfoTest_BaseDataClass' => 'ClassInfoTest_BaseDataClass', 'ClassInfoTest_HasFields' => 'ClassInfoTest_HasFields');
     $this->assertEquals($expect, ClassInfo::dataClassesFor($classes[2]));
 }
Ejemplo n.º 11
0
 /**
  * @refactor move to SQLQuery
  * @todo fix hack
  */
 protected function applyBaseTableFields()
 {
     $classes = ClassInfo::dataClassesFor($this->modelClass);
     $fields = array("`" . ClassInfo::baseDataClass($this->modelClass) . '`.*');
     if ($this->modelClass != $classes[0]) {
         $fields[] = '`' . $classes[0] . '`.*';
     }
     //$fields = array_keys($model->db());
     $fields[] = '`' . $classes[0] . '`.ClassName AS RecordClassName';
     return $fields;
 }
 /**
  * @return JoinSpecification[]
  */
 public function build()
 {
     $specs = array();
     $relation_name = $this->alias->getName();
     $child_class = $this->relations[$relation_name];
     $child_hierarchy = ClassInfo::dataClassesFor($child_class);
     $base_child_class = array_shift($child_hierarchy);
     $class_name = ClassInfo::baseDataClass($this->base_entity);
     $specs[] = new JoinSpecification($child_class, $child_class . '.ID = ' . $class_name . '.' . $relation_name . 'ID');
     $this->base_table = $base_child_class;
     return $specs;
 }
	/**
	 * Most of the code below was copied from ManyManyComplexTableField.
	 * Painful, but necessary, until PHP supports multiple inheritance.
	 */
	

		
	function __construct($controller, $name, $sourceClass, $fileFieldName = null, $fieldList = null, $detailFormFields = null, $sourceFilter = "", $sourceSort = "", $sourceJoin = "") {

		parent::__construct($controller, $name, $sourceClass, $fileFieldName, $fieldList, $detailFormFields, $sourceFilter, $sourceSort, $sourceJoin);
		$manyManyTable = false;
		$classes = array_reverse(ClassInfo::ancestry($this->controllerClass()));
		foreach($classes as $class) {
			if($class != "Object") {
				$singleton = singleton($class);
				$manyManyRelations = $singleton->uninherited('many_many', true);
				if(isset($manyManyRelations) && array_key_exists($this->name, $manyManyRelations)) {
					$this->manyManyParentClass = $class;
					$manyManyTable = $class . '_' . $this->name;
					break;
				}
				$belongsManyManyRelations = $singleton->uninherited( 'belongs_many_many', true );
				 if( isset( $belongsManyManyRelations ) && array_key_exists( $this->name, $belongsManyManyRelations ) ) {
					$this->manyManyParentClass = $class;
					
					// @modification http://open.silverstripe.org/ticket/5194
					$manyManyClass = $belongsManyManyRelations[$this->name];
					$manyManyRelations = singleton($manyManyClass)->uninherited('many_many', true);
					foreach($manyManyRelations as $manyManyRelationship => $manyManyChildClass)
						if ($manyManyChildClass == $class)
							break;
					
					$manyManyTable = $manyManyClass . '_' . $manyManyRelationship;
					break;
				}
			}
		}
		if(!$manyManyTable) user_error("I could not find the relation $this->name in " . $this->controllerClass() . " or any of its ancestors.",E_USER_WARNING);		
		$this->manyManyTable = $manyManyTable;
		$tableClasses = ClassInfo::dataClassesFor($this->sourceClass);
		$source = array_shift($tableClasses);
		$sourceField = $this->sourceClass;
		if($this->manyManyParentClass == $sourceField)
			$sourceField = 'Child';
		$parentID = $this->controller->ID;
		
		$this->sourceJoin .= " LEFT JOIN \"$manyManyTable\" ON (\"$source\".\"ID\" = \"{$sourceField}ID\" AND \"$manyManyTable\".\"{$this->manyManyParentClass}ID\" = '$parentID')";
		
		$this->joinField = 'Checked';
		if(isset($_REQUEST['ctf'][$this->Name()]['only_related']))
		  $this->OnlyRelated = $_REQUEST['ctf'][$this->Name()]['only_related'];

		$this->addPermission('only_related');
		
		// If drag-and-drop is enabled, we need to turn on the only related filter
		if($this->ShowAll() && SortableDataObject::is_sortable_many_many($this->sourceClass()))
			  $this->OnlyRelated = '1';
		
	}
 /**
  * @return JoinSpecification[]
  */
 public function build()
 {
     $specs = array();
     $relation_name = $this->alias->getName();
     $class_name = ClassInfo::baseDataClass($this->base_entity);
     $child_class = $this->relations[$relation_name];
     $child_hierarchy = ClassInfo::dataClassesFor($child_class);
     $base_child_class = array_shift($child_hierarchy);
     $join_field = $this->base_entity->getRemoteJoinField($relation_name, 'has_many');
     $specs[] = new JoinSpecification($base_child_class, $base_child_class . '.' . $join_field . ' = ' . $class_name . '.ID');
     $this->base_table = $base_child_class;
     $this->query->addAndCondition(QueryCriteria::equal("{$base_child_class}.ClassName", $child_class));
     return $specs;
 }
    public function onAfterWrite()
    {
        parent::onAfterWrite();
        $ID = $this->owner->ID;
        $className = $this->owner->ClassName;
        $subClasses = ClassInfo::dataClassesFor($className);
        $versionsToDelete = array();
        $version_limit = Config::inst()->get('VersionTruncator', 'version_limit');
        if (is_numeric($version_limit)) {
            $search = DB::query('SELECT "RecordID", "Version" FROM "SiteTree_versions"
				 WHERE "RecordID" = ' . $ID . ' AND "ClassName" = \'' . $className . '\'
				 AND "PublisherID" > 0
				 ORDER BY "LastEdited" DESC LIMIT ' . $version_limit . ', 200');
            foreach ($search as $row) {
                array_push($versionsToDelete, array('RecordID' => $row['RecordID'], 'Version' => $row['Version']));
            }
        }
        $draft_limit = Config::inst()->get('VersionTruncator', 'draft_limit');
        if (is_numeric($draft_limit)) {
            $search = DB::query('SELECT "RecordID", "Version" FROM "SiteTree_versions"
				 WHERE "RecordID" = ' . $ID . ' AND "ClassName" = \'' . $className . '\'
				 AND "PublisherID" = 0
				 ORDER BY "LastEdited" DESC LIMIT ' . $draft_limit . ', 200');
            foreach ($search as $row) {
                array_push($versionsToDelete, array('RecordID' => $row['RecordID'], 'Version' => $row['Version']));
            }
        }
        $delete_old_page_types = Config::inst()->get('VersionTruncator', 'delete_old_page_types');
        if ($delete_old_page_types) {
            $search = DB::query('SELECT "RecordID", "Version" FROM "SiteTree_versions"
				 WHERE "RecordID" = ' . $ID . ' AND "ClassName" != \'' . $className . '\'');
            foreach ($search as $row) {
                array_push($versionsToDelete, array('RecordID' => $row['RecordID'], 'Version' => $row['Version']));
            }
        }
        /* If versions to delete, start deleting */
        if (count($versionsToDelete) > 0) {
            $affected_tables = array();
            foreach ($subClasses as $subclass) {
                $versionsTable = $subclass . '_versions';
                foreach ($versionsToDelete as $d) {
                    DB::query('DELETE FROM "' . $versionsTable . '"' . ' WHERE "RecordID" = ' . $d['RecordID'] . ' AND "Version" = ' . $d['Version']);
                    if (DB::affectedRows() == 1) {
                        array_push($affected_tables, $versionsTable);
                    }
                }
            }
            $this->vacuumTables($affected_tables);
        }
    }
 public function importPass()
 {
     if (ImportHelper::is_a($this->targetClass, 'SiteTree')) {
         throw new InvalidArgumentException("Don't run TruncateImporter on a SiteTree class");
     }
     // Check extensions
     if (!Object::has_extension($this->targetClass, 'LegacyDataObject')) {
         throw new Exception($this->targetClass . " does not have the LegacyDataObject extension");
     }
     // Update remote table to include _ImportedID column
     $this->setupRemoteTable();
     // Delete all existing records
     $existingRecords = DataObject::get($this->targetClass);
     $existingCount = $existingRecords->count();
     // Get other records
     $query = $this->getRemoteObjectsQuery();
     $remoteObjects = $this->task->query($query);
     $remoteCount = $remoteObjects->numRecords();
     // Start
     $this->task->message(" * Replacing {$existingCount} records with {$remoteCount} ones");
     // Truncate all tables
     $tables = ClassInfo::dataClassesFor($this->targetClass);
     foreach ($tables as $table) {
         DB::query('TRUNCATE "' . $table . '"');
     }
     $this->task->message(" * " . count($tables) . " tables truncated");
     // Add all objects
     $total = 0;
     foreach ($remoteObjects as $remoteObject) {
         // Show progress indicator
         $this->task->progress(++$total, $remoteCount);
         // Make new object
         $class = isset($remoteObject['ClassName']) && ImportHelper::is_a($remoteObject['ClassName'], $this->targetClass) ? $remoteObject['ClassName'] : $this->targetClass;
         // Direct copy data into the new object
         $localObject = $class::create();
         foreach ($remoteObject as $field => $value) {
             $localObject->{$field} = $value;
         }
         $localObject->LegacyID = $remoteObject['ID'];
         $localObject->write(false, true);
     }
     // Bulk update remote table
     $conn = $this->task->getRemoteConnection();
     $baseTable = $this->getRemoteBaseTable();
     $conn->query('UPDATE "' . $baseTable . '" SET "_ImportedID" = "ID", "_ImportedDate" = NOW()');
     // Done!
     $this->task->message(" * Result: {$total} added");
 }
 /**
  * @covers ClassInfo::dataClassesFor()
  */
 public function testDataClassesFor()
 {
     $expect = array('ClassInfoTest_BaseDataClass' => 'ClassInfoTest_BaseDataClass', 'ClassInfoTest_HasFields' => 'ClassInfoTest_HasFields', 'ClassInfoTest_WithRelation' => 'ClassInfoTest_WithRelation', 'ClassInfoTest_WithCustomTable' => 'ClassInfoTest_WithCustomTable');
     $classes = array('ClassInfoTest_BaseDataClass', 'ClassInfoTest_NoFields', 'ClassInfoTest_HasFields');
     ClassInfo::reset_db_cache();
     $this->assertEquals($expect, ClassInfo::dataClassesFor($classes[0]));
     ClassInfo::reset_db_cache();
     $this->assertEquals($expect, ClassInfo::dataClassesFor(strtoupper($classes[0])));
     ClassInfo::reset_db_cache();
     $this->assertEquals($expect, ClassInfo::dataClassesFor($classes[1]));
     $expect = array('ClassInfoTest_BaseDataClass' => 'ClassInfoTest_BaseDataClass', 'ClassInfoTest_HasFields' => 'ClassInfoTest_HasFields');
     ClassInfo::reset_db_cache();
     $this->assertEquals($expect, ClassInfo::dataClassesFor($classes[2]));
     ClassInfo::reset_db_cache();
     $this->assertEquals($expect, ClassInfo::dataClassesFor(strtolower($classes[2])));
 }
 public function getCMSFields()
 {
     $fields = parent::getCMSFields();
     $types = ClassInfo::dataClassesFor('DataObject');
     array_shift($types);
     asort($types);
     $source = array_combine($types, $types);
     $fields->replaceField('Title', new DropdownField('Title', _t('Solr.TYPE_CONFIG_TITLE', 'Data type'), $source));
     if ($this->Title) {
         $keys = $this->getFieldsFor($this->Title);
         $vals = array('default' => _t('Solr.DEFAULT_MAPPING', 'Default type'), ':field_as' => _t('Solr.CASE_INSENSITIVE', 'Case Insensitive text'), ':field_ms' => _t('Solr.CASE_SENSITIVE', 'Case Sensitive, untokenised text'));
         $fields->replaceField('FieldMappings', new KeyValueField('FieldMappings', _t('Solr.FIELD_MAPPINGS', 'Indexed fields'), $keys, $vals, $this->FieldMappings));
     } else {
         $fields->removeByName('FieldMappings');
     }
     return $fields;
 }
 /**
  * Gets the table which contains the sort field.
  *
  * @param DataList $list
  * @return string
  */
 public function getSortTable(DataList $list)
 {
     $field = $this->getSortField();
     if ($list instanceof ManyManyList) {
         $extra = $list->getExtraFields();
         $table = $list->getJoinTable();
         if ($extra && array_key_exists($field, $extra)) {
             return $table;
         }
     }
     $classes = ClassInfo::dataClassesFor($list->dataClass());
     foreach ($classes as $class) {
         if (singleton($class)->hasOwnTableDatabaseField($field)) {
             return $class;
         }
     }
     throw new Exception("Couldn't find the sort field '{$field}'");
 }
 public function run($request)
 {
     HTTP::set_cache_age(0);
     increase_time_limit_to();
     // This can be a time consuming task
     $classes = ClassInfo::dataClassesFor('DataObject');
     $conn = DB::getConn();
     $go = $request->getVar('go');
     if (!$go) {
         echo 'Set ?go=1 to really delete the fields';
         echo '<hr/>';
     }
     foreach ($classes as $class) {
         $hasTable = ClassInfo::hasTable($class);
         if (!$hasTable) {
             continue;
         }
         $toDrop = array();
         $fields = $class::database_fields($class);
         $list = $conn->fieldList($class);
         foreach ($list as $fieldName => $type) {
             if ($fieldName == 'ID') {
                 continue;
             }
             if (!isset($fields[$fieldName])) {
                 $toDrop[] = $fieldName;
             }
         }
         if (empty($toDrop)) {
             continue;
         }
         if ($go) {
             $this->dropColumns($class, $toDrop);
             DB::alteration_message("Dropped " . implode(',', $toDrop) . " for {$class}", "obsolete");
         } else {
             DB::alteration_message("Would drop " . implode(',', $toDrop) . " for {$class}", "obsolete");
         }
     }
 }
 /**
  * Returns a filtered list of fields which could contain shortcodes.
  *
  * @param String
  * @return Array Map of class names to an array of field names on these classes.
  */
 function getShortcodeFields($class)
 {
     $fields = array();
     $ancestry = array_values(ClassInfo::dataClassesFor($class));
     foreach ($ancestry as $ancestor) {
         if (ClassInfo::classImplements($ancestor, 'TestOnly')) {
             continue;
         }
         $ancFields = DataObject::custom_database_fields($ancestor);
         if ($ancFields) {
             foreach ($ancFields as $ancFieldName => $ancFieldSpec) {
                 if (preg_match($this->fieldSpecRegex, $ancFieldSpec)) {
                     if (!@$fields[$ancestor]) {
                         $fields[$ancestor] = array();
                     }
                     $fields[$ancestor][$ancFieldName] = $ancFieldSpec;
                 }
             }
         }
     }
     return $fields;
 }
 public function run($request)
 {
     $classes = ClassInfo::dataClassesFor('DataObject');
     $conn = DB::getConn();
     foreach ($classes as $class) {
         $fields = $class::database_fields($class);
         $list = $conn->fieldList($class);
         foreach ($list as $fieldName => $type) {
             if ($fieldName == 'ID') {
                 continue;
             }
             if (strpos($fieldName, '_obsolete_') === 0) {
                 $this->dropColumns($class, array($fieldName));
                 DB::alteration_message("Dropped {$fieldName}", "obsolete");
                 continue;
             }
             if (!isset($fields[$fieldName])) {
                 $conn->dontRequireField($class, $fieldName);
             }
         }
     }
 }
Ejemplo n.º 23
0
 /**
  * Get the name of the base table for this object
  */
 public function baseTable()
 {
     $tableClasses = ClassInfo::dataClassesFor($this->class);
     return array_shift($tableClasses);
 }
Ejemplo n.º 24
0
 public function getAlias($join_type = QueryAlias::INNER)
 {
     $join = array();
     foreach ($this->alias as $alias) {
         if ($alias->getJoinType() !== $join_type) {
             continue;
         }
         $child = $alias->getName();
         $has_many = Config::inst()->get(get_class($this->base_entity), 'has_many');
         $class_name = ClassInfo::baseDataClass($this->base_entity);
         if (!is_null($has_many)) {
             $has_many_classes = array_flip($has_many);
             if (array_key_exists($child, $has_many_classes)) {
                 $tableClasses = ClassInfo::dataClassesFor($child);
                 $baseClass = array_shift($tableClasses);
                 $joinField = $this->base_entity->getRemoteJoinField($has_many_classes[$child], 'has_many');
                 $join[$baseClass] = $baseClass . '.' . $joinField . ' = ' . $class_name . '.ID';
                 $this->addAndCondition(QueryCriteria::equal("{$baseClass}.ClassName", $child));
             }
         }
         $has_many_many = Config::inst()->get(get_class($this->base_entity), 'many_many');
         if (!is_null($has_many_many)) {
             $has_many_many_classes = array_flip($has_many_many);
             if (array_key_exists($child, $has_many_many_classes)) {
                 $base_entity_name = get_class($this->base_entity);
                 $component = $has_many_many_classes[$child];
                 $joinTable = "{$base_entity_name}_{$component}";
                 $parentField = $base_entity_name . "ID";
                 $childField = $child . "ID";
                 $join[$joinTable] = $joinTable . '.' . $parentField . ' = ' . $class_name . '.ID';
                 $join[$child] = $child . '.ID = ' . $joinTable . '.' . $childField;
             }
         }
         $has_one = Config::inst()->get(get_class($this->base_entity), 'has_one');
         if (!is_null($has_one)) {
             if (array_key_exists($child, $has_one)) {
                 $table = $has_one[$child];
                 $join[$table] = $has_one[$child] . '.ID = ' . $class_name . '.' . $child . 'ID';
             } else {
                 $has_one_classes = array_flip($has_one);
                 if (array_key_exists($child, $has_one_classes)) {
                     $join[$child] = $child . '.ID = ' . $class_name . '.' . $has_one_classes[$child] . 'ID';
                 }
             }
         }
         $belongs_many_many = Config::inst()->get(get_class($this->base_entity), 'belongs_many_many');
         if (!is_null($belongs_many_many)) {
             $belongs_many_many_classes = array_flip($belongs_many_many);
             if (array_key_exists($child, $belongs_many_many_classes)) {
                 $child_many_many = Config::inst()->get($child, 'many_many');
                 $child_many_many_classes = array_flip($child_many_many);
                 $component_name = $child_many_many_classes[$class_name];
                 list($parentClass, $componentClass, $child_join_field, $join_field, $join_table) = Singleton($child)->many_many($component_name);
                 $join[$join_table] = $join_table . '`.' . $join_field . ' = `' . $class_name . '`.ID';
                 $join[$child] = $child . '`.ID = `' . $join_table . '`.' . $child_join_field;
             }
         }
         if ($alias->hasSubAlias()) {
             $join = array_merge($join, $alias->subAlias($join_type));
         }
     }
     return $join;
 }
 function baseTable()
 {
     $record = $this->record;
     $classes = ClassInfo::dataClassesFor($record->ClassName);
     return array_pop($classes);
 }
Ejemplo n.º 26
0
 /**
  * Ensure that if a query has an order by clause, those columns are present in the select.
  * 
  * @param SQLQuery $query
  * @return null
  */
 protected function ensureSelectContainsOrderbyColumns($query, $originalSelect = array())
 {
     $tableClasses = ClassInfo::dataClassesFor($this->dataClass);
     $baseClass = array_shift($tableClasses);
     if ($orderby = $query->getOrderBy()) {
         $newOrderby = array();
         $i = 0;
         foreach ($orderby as $k => $dir) {
             $newOrderby[$k] = $dir;
             // don't touch functions in the ORDER BY or public function calls
             // selected as fields
             if (strpos($k, '(') !== false) {
                 continue;
             }
             $col = str_replace('"', '', trim($k));
             $parts = explode('.', $col);
             // Pull through SortColumn references from the originalSelect variables
             if (preg_match('/_SortColumn/', $col)) {
                 if (isset($originalSelect[$col])) {
                     $query->selectField($originalSelect[$col], $col);
                 }
                 continue;
             }
             if (count($parts) == 1) {
                 $databaseFields = DataObject::database_fields($baseClass);
                 // database_fields() doesn't return ID, so we need to
                 // manually add it here
                 $databaseFields['ID'] = true;
                 if (isset($databaseFields[$parts[0]])) {
                     $qualCol = "\"{$baseClass}\".\"{$parts[0]}\"";
                 } else {
                     $qualCol = "\"{$parts['0']}\"";
                 }
                 // remove original sort
                 unset($newOrderby[$k]);
                 // add new columns sort
                 $newOrderby[$qualCol] = $dir;
                 // To-do: Remove this if block once SQLQuery::$select has been refactored to store getSelect()
                 // format internally; then this check can be part of selectField()
                 $selects = $query->getSelect();
                 if (!isset($selects[$col]) && !in_array($qualCol, $selects)) {
                     $query->selectField($qualCol);
                 }
             } else {
                 $qualCol = '"' . implode('"."', $parts) . '"';
                 if (!in_array($qualCol, $query->getSelect())) {
                     unset($newOrderby[$k]);
                     $newOrderby["\"_SortColumn{$i}\""] = $dir;
                     $query->selectField($qualCol, "_SortColumn{$i}");
                     $i++;
                 }
             }
         }
         $query->setOrderBy($newOrderby);
     }
 }
 /**
  * Returns the base class name of the owner used for SQL
  *
  * @return string
  */
 public function getBaseClassName()
 {
     $tableClasses = ClassInfo::dataClassesFor($this->owner->class);
     $baseClassName = array_shift($tableClasses);
     return $baseClassName;
 }
 /**
  * Get the parent of this class.
  * @return DataObject
  */
 public function getParent($filter = null)
 {
     if ($p = $this->owner->__get("ParentID")) {
         $tableClasses = ClassInfo::dataClassesFor($this->owner->class);
         $baseClass = array_shift($tableClasses);
         return DataObject::get_one($this->owner->class, array(array("\"{$baseClass}\".\"ID\"" => $p), $filter));
     }
 }
Ejemplo n.º 29
0
 /**
  * Get the parent of this class.
  * @return DataObject
  */
 public function getParent($filter = '')
 {
     if ($p = $this->owner->__get("ParentID")) {
         $tableClasses = ClassInfo::dataClassesFor($this->owner->class);
         $baseClass = array_shift($tableClasses);
         $filter .= $filter ? " AND " : "" . "\"{$baseClass}\".\"ID\" = {$p}";
         return DataObject::get_one($this->owner->class, $filter);
     }
 }
Ejemplo n.º 30
0
 /**
  * Checks the database is in a state to perform security checks.
  * See {@link DatabaseAdmin->init()} for more information.
  *
  * @return bool
  */
 public static function database_is_ready()
 {
     // Used for unit tests
     if (self::$force_database_is_ready !== NULL) {
         return self::$force_database_is_ready;
     }
     if (self::$database_is_ready) {
         return self::$database_is_ready;
     }
     $requiredTables = ClassInfo::dataClassesFor('Member');
     $requiredTables[] = 'Group';
     $requiredTables[] = 'Permission';
     foreach ($requiredTables as $table) {
         // Skip test classes, as not all test classes are scaffolded at once
         if (is_subclass_of($table, 'TestOnly')) {
             continue;
         }
         // if any of the tables aren't created in the database
         if (!ClassInfo::hasTable($table)) {
             return false;
         }
         // HACK: DataExtensions aren't applied until a class is instantiated for
         // the first time, so create an instance here.
         singleton($table);
         // if any of the tables don't have all fields mapped as table columns
         $dbFields = DB::field_list($table);
         if (!$dbFields) {
             return false;
         }
         $objFields = DataObject::database_fields($table, false);
         $missingFields = array_diff_key($objFields, $dbFields);
         if ($missingFields) {
             return false;
         }
     }
     self::$database_is_ready = true;
     return true;
 }