public static function add()
 {
     parent::add();
     self::$facebook_app_id = Installer::getComposerEvent()->getIO()->ask(":: enter your facebook app id: ", "[app_id]");
     self::$facebook_api_secret = Installer::getComposerEvent()->getIO()->ask(":: enter your facebook app secret: ", "[app_secret]");
     File::replaceContent(Installer::getRootDirConfig() . self::getConfigfile(), "[app_id]", self::getFacebookAppId());
     File::replaceContent(Installer::getRootDirConfig() . self::getConfigfile(), "[api_secret]", self::getFacebookApiSecret());
     File::addContent(Installer::getRootDirTheme() . "Includes/Footer.ss", "<% include FacebookLoginLink %>", "SilverStripe</a></small>");
     Installer::getComposerEvent()->getIO()->write(":: added facebookconnect extension");
 }
 /**
  * copy customized extension.yml, classes and templates to silverstripe project which should be availible as skelet
  */
 public static function add()
 {
     File::copy(Installer::getRootDirVendor() . static::getExtension(), Installer::getRootDirConfig());
     Installer::getComposerEvent()->getIO()->write(":: copied " . self::getConfigfile());
     foreach (static::getClasses() as $folder => $class) {
         File::copy(Installer::getRootDirVendor() . $class, Installer::getRootDirCode() . $folder . "/");
         Installer::getComposerEvent()->getIO()->write(":: added class {$class}");
     }
     foreach (static::getTemplates() as $folder => $template) {
         File::copy(Installer::getRootDirVendor() . $template, Installer::getRootDirTheme() . $folder . "/");
         Installer::getComposerEvent()->getIO()->write(":: added template {$template}");
     }
 }
 /**
  * file editing
  * 
  * @param string $filename
  * @param string $content
  * @param string $search
  * @param boolean $replace true if the given content should replace the $search string
  */
 public static function editContent($filename, $content, $search, $replace = false)
 {
     $lines = array();
     $linesTmp = array();
     $changed = false;
     // flag to set true when $search found in content
     // open file to read
     if (($fileHandle = fopen($filename, "r")) !== false) {
         // buffer every line
         while (($buffer = fgets($fileHandle)) !== false) {
             $lines[] = $buffer;
         }
         // close file
         fclose($fileHandle);
     } else {
         Installer::getComposerEvent()->getIO()->write(":: failure reading {$filename} perhaps not exists");
     }
     foreach ($lines as $line) {
         // if searched string found
         if (strpos($line, $search) !== false) {
             // when search string should be replaced
             if ($replace) {
                 $linesTmp[] = str_replace($search, $content, $line);
                 Installer::getComposerEvent()->getIO()->write(":: replaced {$search} with {$content} in {$filename}");
             } else {
                 $linesTmp[] = $line;
                 $linesTmp[] = $content . PHP_EOL;
                 Installer::getComposerEvent()->getIO()->write(":: added {$content} after {$search} to {$filename}");
             }
             $changed = true;
         } else {
             $linesTmp[] = $line;
         }
     }
     // has file changed
     if ($changed) {
         // overwrite file with new content
         file_put_contents($filename, implode('', $linesTmp));
     } else {
         Installer::getComposerEvent()->getIO()->write(":: not added {$content} to {$filename} because {$search} not found");
     }
 }
 public static function add()
 {
     parent::add();
     Installer::getComposerEvent()->getIO()->write(":: added bootstrap-forms extension");
 }