diff --git a/VERSIONS_WIP/29947 b/VERSIONS_WIP/29947
new file mode 100644
index 0000000000000000000000000000000000000000..801d9ae1a6cae3ba097878bd650ec2cda474637a
--- /dev/null
+++ b/VERSIONS_WIP/29947
@@ -0,0 +1 @@
+ - ticket #29947 : Miop Migration Typo3
\ No newline at end of file
diff --git a/library/Class/Import/Typo3.php b/library/Class/Import/Typo3.php
index ce6089b60cebbbc5a36edd75862c007e29af647c..a52fdc6a149169f0b6edb361f753aaeef09f92f7 100644
--- a/library/Class/Import/Typo3.php
+++ b/library/Class/Import/Typo3.php
@@ -90,6 +90,12 @@ class Class_Import_Typo3 {
     $_SERVER['HTTP_HOST']='localhost';
     $logger = Class_Import_Typo3_Logs::getInstance();
 
+    if ('postprocess' == $what) {
+      $logger->addLogRow("\n\n ******** Post-Process effacement des articles pid=-1");
+      $this->postProcess();
+      return $logger->report();
+    }
+
     if ('update' == $what && !$last_update) {
       $logger->addErrorRow("Mode mise à jour demandé sans date de référence");
       return $logger->report();
@@ -217,9 +223,8 @@ class Class_Import_Typo3 {
     $t3news = $this->t3db->findAllSitesSince($update_date);
 
     foreach($t3news as $new) {
-      if ($site = Class_Sitotheque::findFirstByCustomFieldValue(SELF::UID_TYPO3_CF,
-                                                                $new['uid'])) {
-        $this->updateSite($site,$new);
+      if ($site = $this->_getSite($new['uid'])) {
+        $this->updateSite($site, $new);
         continue;
       }
 
@@ -230,6 +235,11 @@ class Class_Import_Typo3 {
   }
 
 
+  protected function _getSite($uid) {
+    return Class_Sitotheque::findFirstByCustomFieldValue(SELF::UID_TYPO3_CF, $uid);
+  }
+
+
   public function importSites() {
     Class_Sitotheque::deleteBy([]);
 
@@ -890,5 +900,41 @@ class Class_Import_Typo3 {
             'tags' => $tags,
             'description' => $new['short']];
   }
-}
-?>
\ No newline at end of file
+
+
+  public function postProcess() {
+    $this
+      ->_cleanArticles()
+      ->_cleanSites();
+  }
+
+
+  protected function _cleanSites() {
+    $this->_cleanModelsBy('findRemovableArticles', '_getSite');
+    return $this;
+  }
+
+
+  protected function _cleanArticles() {
+    foreach(['findRemovableArticles',
+             'findRemovableContents',
+             'findRemovableEvents'] as $method)
+      $this->_cleanModelsBy($method, '_getArticle');
+
+    return $this;
+  }
+
+
+  protected function _cleanModelsBy($db_method, $model_getter) {
+    foreach($this->t3db->$db_method() as $item)
+      if ($model = $this->$model_getter($item['uid']))
+        $this->_cleanModel($model);
+  }
+
+
+  /** @param $model use Trait_Indexable, Trait_CustomFields */
+  protected function _cleanModel($model) {
+    $model->unindex();
+    $model->deleteWithCustomFields();
+  }
+}
\ No newline at end of file
diff --git a/library/Class/Import/Typo3/Db.php b/library/Class/Import/Typo3/Db.php
index e9d5aac5b579da3e384bfda187988e5d69ee12bf..d3d757cae8ada241534cc8dc9d5d82aadedcf2b5 100644
--- a/library/Class/Import/Typo3/Db.php
+++ b/library/Class/Import/Typo3/Db.php
@@ -18,7 +18,7 @@
  * along with BOKEH; if not, write to the Free Software
  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301  USA
  */
-class Class_Import_Typo3_DB {
+class Class_Import_Typo3_Db {
   protected
     $t3db,
     $pages_titles;
@@ -107,6 +107,11 @@ class Class_Import_Typo3_DB {
   }
 
 
+  public function findRemovableArticles() {
+    return $this->t3db->fetchAll("select uid from tt_news where pid=-1");
+  }
+
+
   public function findAllForeignUidForCalendarEventCategory($uid) {
     return $this->t3db->fetchAll("select distinct uid_foreign from tx_cal_event_category_mm where uid_local=" . $uid . " order by sorting");
   }
@@ -117,6 +122,11 @@ class Class_Import_Typo3_DB {
   }
 
 
+  public function findRemovableEvents() {
+    return $this->t3db->fetchAll('select uid from tx_cal_event where pid=-1');
+  }
+
+
   public function findAllContents($page_id=false) {
     $pid_sql='';
     if ($page_id)
@@ -129,4 +139,9 @@ class Class_Import_Typo3_DB {
   public function findAllContentsSince($update_date) {
     return $this->t3db->fetchAll("select * from tt_content where deleted=0 and tstamp>=".$update_date." and hidden=0 and header>'' and bodytext>'' and  (ctype='text' or ctype='textpic') order by uid ASC");
   }
+
+
+  public function findRemovableContents() {
+    return $this->t3db->fetchAll("select uid from tt_content where pid=-1");
+  }
 }
diff --git a/tests/library/Class/Import/Typo3Test.php b/tests/library/Class/Import/Typo3Test.php
index dbea0557ed92df8d0595897a9e9a2b4394859e32..eb6631263976e4d77f17340842f908d963f60daf 100644
--- a/tests/library/Class/Import/Typo3Test.php
+++ b/tests/library/Class/Import/Typo3Test.php
@@ -24,12 +24,12 @@ include_once("Typo3Fixture.php");
 
 
 abstract class Import_Typo3TestCase extends ModelTestCase {
+  protected $_storm_default_to_volatile = true;
   protected $migration;
 
   public function setUp() {
     parent::setUp();
     Class_Import_Typo3_Logs::getInstance()->cleans();
-    Storm_Model_Loader::defaultToVolatile();
 
     $this->mock_sql = Storm_Test_ObjectWrapper::mock();
     $this->old_sql = Zend_Registry::get('sql');
@@ -58,7 +58,6 @@ abstract class Import_Typo3TestCase extends ModelTestCase {
 
   public function tearDown() {
     Zend_Registry::set('sql', $this->old_sql);
-    Storm_Model_Loader::defaultToDb();
     parent::tearDown();
   }
 }
@@ -1109,4 +1108,111 @@ class Import_Typo3AdvicesTest extends Import_Typo3TestCase {
   public function userKeyShouldBeTestUser() {
     $this->assertEquals('--0--test_user', $this->advice->getUserKey());
   }
+}
+
+
+
+
+class Import_Typo3PostProcessTest extends Import_Typo3TestCase {
+  public function setUp() {
+    parent::setUp();
+
+    $this->fixture('Class_Article',
+                   ['id' => 123456789,
+                    'titre' => 'Mon super titre',
+                    'contenu' => 'Mon super contenu'])
+         ->setCustomField('uid_typo3', '3455')
+         ->saveWithCustomFields();
+
+    $this->fixture('Class_Article',
+                   ['id' => 888,
+                    'titre' => 'Mon super titre 2',
+                    'contenu' => 'Mon super contenu 2'])
+         ->setCustomField('uid_typo3', '4897')
+         ->saveWithCustomFields();
+
+    $this->fixture('Class_Article',
+                   ['id' => 555,
+                    'titre' => 'Mon super event',
+                    'contenu' => 'Mon super contenu'])
+         ->setCustomField('uid_typo3', '8938')
+         ->saveWithCustomFields();
+
+    $this->fixture('Class_Article',
+                   ['id' => 999,
+                    'titre' => 'Mon super titre 3',
+                    'contenu' => 'Mon super contenu 3'])
+         ->setCustomField('uid_typo3', '777')
+         ->saveWithCustomFields();
+
+    $this->fixture('Class_Sitotheque',
+                   ['id' => 1004,
+                    'titre' => 'Testing sito',
+                    'date_maj' => '2015-11-18 10:47:37',
+                    'url' => 'http://my.server.com',
+                    'tags' => '',
+                    'description' => 'My super duper hyper cooler desc'])
+         ->setCustomField('uid_typo3', '8883')
+         ->saveWithCustomFields();
+
+    $this->fixture('Class_Sitotheque',
+                   ['id' => 1005,
+                    'titre' => 'Testing sito not removable',
+                    'date_maj' => '2015-11-18 10:12:37',
+                    'url' => 'http://your.server.com',
+                    'tags' => '',
+                    'description' => 'My desc'])
+         ->setCustomField('uid_typo3', '8882')
+         ->saveWithCustomFields();
+
+    $this->migration
+      ->setTypo3DB($this->mock()
+                   ->whenCalled('findRemovableArticles')->answers([['uid' => '3455'],
+                                                                   ['uid' => '8883']])
+                   ->whenCalled('findRemovableContents')->answers([ ['uid' => '4897'] ])
+                   ->whenCalled('findRemovableEvents')->answers([ ['uid' => '8938'] ]))
+      ->postProcess();
+  }
+
+
+  /** @test */
+  public function shouldDeleteNews() {
+    $this->assertNull(Class_Article::find(123456789));
+  }
+
+
+  /** @test */
+  public function customFieldsShouldBeDeleted() {
+    $this->assertNull(Class_CustomField_Value::findFirstBy(['value' => '3455']));
+  }
+
+
+  /** @test */
+  public function shouldDeletePages() {
+    $this->assertNull(Class_Article::find(888));
+  }
+
+
+  /** @test */
+  public function shouldDeleteEvents() {
+    $this->assertNull(Class_Article::find(555));
+  }
+
+
+  /** @test */
+  public function shouldNotDeleteAllArticles() {
+    $this->assertNotNull(Class_Article::find(999));
+  }
+
+
+  /** @test */
+  public function shouldDeleteSito() {
+    $this->assertNull(Class_Sitotheque::find(1004));
+  }
+
+
+  /** @test */
+  public function shouldNotDeleteAllSitos() {
+    $this->assertNotNull(Class_Sitotheque::find(1005));
+  }
 }
\ No newline at end of file