import os
import json

from scrapi import settings
from scrapi.util import make_dir
from scrapi.util import doc_id_to_path


class BaseStorage(object):
    METHOD = None

    # :: Str -> Str -> Nothing
    def _store(string, path):
        raise NotImplementedError('No store method')

    # :: Str -> Bool -> [RawDocument]
    def iter_raws(source, include_normalized=False):
        raise NotImplementedError('No iter raws method')

    # :: Str -> Str
    def get_as_string(self, path):
        raise NotImplementedError('No get as string method')

    # :: Str -> Dict
    def get_as_json(self, path):
        return json.loads(self.get_as_string(path))

    # :: Str -> Str
    def _build_path(self, raw_doc):
        path = [
            settings.ARCHIVE_DIRECTORY,
            raw_doc.get('source'),
            doc_id_to_path(raw_doc.get('docID')),
            raw_doc.get('timestamp')
        ]

        path = os.path.join(*path)
        make_dir(path)

        return path

    # :: NormalizedDocument -> Nothing
    def store_normalized(self, raw_doc, document, overwrite=False):
        path = self._build_path(raw_doc)
        manifest = settings.MANIFESTS[document.get('source')]
        manifest_update = {
            'normalizeVersion': manifest['version']
        }

        self.update_manifest(path, manifest_update)

        path = os.path.join(path, 'normalized.json')

        self._store(json.dumps(document.attributes), path, overwrite=overwrite)

    # :: RawDocument -> Nothing
    def store_raw(self, document):
        manifest = settings.MANIFESTS[document.get('source')]
        doc_name = 'raw.{}'.format(manifest['fileFormat'])
        path = self._build_path(document)
        manifest = {
            'timestamp': document.get('timestamp'),
            'source': document.get('source'),
            'consumeVersion': manifest['version']
        }

        self.update_manifest(path, manifest)

        path = os.path.join(path, doc_name)

        self._store(document.get('doc'), path)

    # :: RawDocument -> Dict -> Nothing
    def update_manifest(self, path, fields):
        path = os.path.join(path, 'manifest.json')
        try:
            manifest = self.get_as_json(path)
        except Exception:  # TODO Make this more specific
            manifest = {}

        manifest.update(fields)
        self._store(json.dumps(manifest), path, overwrite=True)

@@ -869,21 +869,17 @@
  raw_doc
-.get(
+%5B
 'timesta
@@ -880,18 +880,38 @@
 imestamp
-')
+s'%5D%5B'consumeFinished'%5D
 %0A       
@@ -1747,17 +1747,25 @@
        '
-t
+consumedT
 imestamp
@@ -1775,21 +1775,17 @@
 document
-.get(
+%5B
 'timesta
@@ -1786,18 +1786,38 @@
 imestamp
-')
+s'%5D%5B'consumeFinished'%5D
 ,%0A      
@@ -1840,29 +1840,25 @@
 document
-.get(
+%5B
 'source'
 ),%0A     
@@ -1841,33 +1841,33 @@
 ocument%5B'source'
-)
+%5D
 ,%0A            'c

Use the newest timestamp format when storing documents