#include "fa_dumper.h"

#include <saas/protos/rtyserver.pb.h>

#include <google/protobuf/messagext.h>

#include <kernel/multipart_archive/multipart.h>
#include <kernel/multipart_archive/config/config.h>

#include <yweb/protos/indexeddoc.pb.h>

#include <util/stream/file.h>

namespace NRTYServer {
namespace {

bool Deserialize(const TBlob& blob, NRTYServer::TParsedDoc& parsedDoc) {
    try {
        TMemoryInput inp(blob.Data(), blob.Size());
        ::google::protobuf::io::TProtoSerializer::Load(&inp, parsedDoc);
    } catch (...) {
        ERROR_LOG << "Cannot parse document: " << CurrentExceptionMessage() << Endl;
        return false;
    }
    return true;
}

class TFADumperImpl final : public TFADumper {
private:
    TArchiveOwner::TPtr FullArc;
public:
    TFADumperImpl(const TFADumper::TArgs& args) {
        NRTYArchive::TMultipartConfig layerConfig;
        layerConfig.Compression = NRTYArchive::IArchivePart::TType::COMPRESSED;
        FullArc = TArchiveOwner::Create(TFsPath(args.IndexDir) / "indexfullarc.full", layerConfig, 0, true);
    }

    bool Open() override {
        return true;
    }

    bool Close() override {
        return true;
    }

    bool Run(TFADumper::THandler& handler, TAtomic* stopFlag) override {
        for (auto iter = FullArc->CreateIterator(); iter->IsValid(); iter->Next()) {
            if (stopFlag && AtomicGet(*stopFlag)) {
                return false;
            }

            const ui32 realDocId = iter->GetDocid();
            if (FullArc->IsRemoved(realDocId)) {
                continue;
            }

            const TBlob document = iter->GetDocument();
            NRTYServer::TParsedDoc parsedDoc;
            if (!Deserialize(document, parsedDoc))
                continue;

            if (!handler.OnParsedDoc(realDocId, parsedDoc))
                return false;
        }
        return true;
    }

    virtual ~TFADumperImpl() {
        try {
            Close();
            FullArc.Drop();
        } catch (...) {
            Y_FAIL();
        }
    }
};

} // anonymous namespaces

THolder<TFADumper> TFADumper::Create(const TArgs& args) {
    return THolder<TFADumper>(new TFADumperImpl(args));
}
} // namespace NRTYServer



