aboutsummaryrefslogtreecommitdiffstats
path: root/library/cpp/streams/factory/open_by_file_extension/factory.cpp
blob: 8836f3cdcd9702b58eb3491efcd6aab7d4c1f0d9 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
#include "factory.h"

#include <library/cpp/streams/bzip2/bzip2.h>
#include <library/cpp/streams/factory/open_common/factory.h>
#include <util/stream/holder.h>
#include <util/stream/file.h>
#include <util/stream/output.h>
#include <util/stream/zlib.h>
#include <util/system/file.h>
#include <util/generic/ptr.h>
#include <util/generic/string.h>
#include <util/generic/store_policy.h>

namespace {
    template <class T, class TDecoder>
    class TCompressed: public TEmbedPolicy<T>, public TDecoder {
    public:
        template <class C>
        inline TCompressed(const C& c)
            : TEmbedPolicy<T>(c)
            , TDecoder(TEmbedPolicy<T>::Ptr())
        {
        }

        template <class C>
        inline TCompressed(const C& c, size_t compressionLevel, size_t buflen)
            : TEmbedPolicy<T>(c)
            , TDecoder(this->Ptr(), compressionLevel, buflen)
        {
        }

        ~TCompressed() override {
        }
    };

    class TGZipCompress: public TZLibCompress {
    public:
        TGZipCompress(IOutputStream* output)
            : TZLibCompress(output, ZLib::GZip)
        {
        }

        TGZipCompress(IOutputStream* output, size_t compressionLevel, size_t buflen)
            : TZLibCompress(output, ZLib::GZip, compressionLevel, buflen)
        {
        }
    };
}

THolder<IInputStream> OpenInput(const TString& url) {
    if (!url || url == TStringBuf("-")) {
        return OpenStdin();
    }

    if (url.EndsWith(TStringBuf(".gz"))) {
        return MakeHolder<TCompressed<TFileInput, TBufferedZLibDecompress>>(url);
    }

    if (url.EndsWith(TStringBuf(".bz2"))) {
        return MakeHolder<TCompressed<TFileInput, TBZipDecompress>>(url);
    }

    return MakeHolder<TFileInput>(url);
}

THolder<IOutputStream> OpenOutput(const TString& url, ECompression compressionLevel, size_t buflen) {
    if (!url || url == TStringBuf("-")) {
        return MakeHolder<TFileOutput>(Duplicate(1));
    } else if (url.EndsWith(TStringBuf(".gz"))) {
        return MakeHolder<TCompressed<TFileOutput, TGZipCompress>>(url, size_t(compressionLevel), buflen);
    } else if (url.EndsWith(TStringBuf(".bz2"))) {
        return MakeHolder<TCompressed<TFileOutput, TBZipCompress>>(url, size_t(compressionLevel), buflen);
    }

    return MakeHolder<TFileOutput>(url);
}