Revision 47:273bd328b215

View differences:

common/ComposerFileIndex.cpp
1
/* -*- c-basic-offset: 4 indent-tabs-mode: nil -*-  vi:set ts=8 sts=4 sw=4: */
2

  
3
#include "ComposerFileIndex.h"
4
#include "TypeRegistrar.h"
5

  
6
#include <QMutexLocker>
7
#include <QDir>
8

  
9
#include "base/TempDirectory.h"
10
#include "base/Exceptions.h"
11

  
12
using namespace Dataquay;
13

  
14

  
15
namespace ClassicalData {
16

  
17
ComposerFileIndex *
18
ComposerFileIndex::getInstance()
19
{
20
    static ComposerFileIndex instance;
21
    return &instance;
22
}
23

  
24
ComposerFileIndex::ComposerFileIndex() :
25
    m_bs(0),
26
    m_index(0)
27
{
28
    try {
29
	m_indexFileName = getIndexFileName();
30
    } catch (DirectoryCreationFailed f) {
31
        std::cerr << "ComposerFileIndex: ERROR: Failed to find or create index directory: " << f.what() << std::endl;
32
        return;
33
    }
34

  
35
    m_bs = new BasicStore;
36
    m_index = new TransactionalStore(m_bs);
37

  
38
    TypeRegistrar::addMappings(m_bs, 0);
39

  
40
    if (QFile(m_indexFileName).exists()) {
41
	m_bs->import(QUrl::fromLocalFile(m_indexFileName),
42
                     BasicStore::ImportIgnoreDuplicates);
43
	//!!! catch
44
    }
45
}
46

  
47
ComposerFileIndex::~ComposerFileIndex()
48
{
49
    delete m_index;
50
    delete m_bs;
51
}
52

  
53
QString
54
ComposerFileIndex::getIndexFileName()
55
{
56
    QDir d = TempDirectory::getInstance()->getContainingPath();
57
    QString n("index");
58
    QFileInfo fi(d.filePath(n));
59

  
60
    if ((fi.exists() && !fi.isDir()) ||
61
        (!fi.exists() && !d.mkdir(n))) {
62
        throw DirectoryCreationFailed(fi.filePath());
63
    }
64

  
65
    return QDir(fi.filePath()).filePath("composer-details.ttl");
66
}
67

  
68
QString
69
ComposerFileIndex::getComposerDirectoryName()
70
{
71
    QDir d = TempDirectory::getInstance()->getContainingPath();
72
    QString n("composers");
73
    QFileInfo fi(d.filePath(n));
74

  
75
    if ((fi.exists() && !fi.isDir()) ||
76
        (!fi.exists() && !d.mkdir(n))) {
77
        throw DirectoryCreationFailed(fi.filePath());
78
    }
79

  
80
    return fi.filePath();
81
}
82

  
83
void
84
ComposerFileIndex::loadFor(Uri composerUri, Store *store)
85
{
86
    if (!m_index) {
87
	std::cerr << "ComposerFileIndex::loadFor: No index!" << std::endl;
88
	return;
89
    }
90
    updateIndex();
91

  
92
    Triple pattern(Node(), "foaf:primaryTopic", composerUri);
93
    Triples results = m_index->match(pattern);
94
    std::cerr << "ComposerFileIndex::loadFor: " << results.size() << " file(s) for composer " << composerUri << std::endl;
95

  
96
    bool loadedSomething = false;
97

  
98
    foreach (Triple t, results) {
99
        try {
100
            BasicStore *b = BasicStore::load(QUrl(t.a.value));
101
            //!!! This is hardly the most efficient!
102
            Triples all = b->match(Triple());
103
            //!!! There is no Store::add(Triples)
104
            foreach (Triple t, all) {
105
                store->add(t);
106
            }
107
        } catch (...) { } //!!!???
108
    }
109

  
110
    return loadedSomething;
111
}
112

  
113
void
114
ComposerFileIndex::composerFileAdded(QString filepath)
115
{
116
    index(QUrl::fromLocalFile(filepath));
117
}    
118

  
119
void
120
ComposerFileIndex::updateIndex()
121
{
122
    QMutexLocker locker(&m_mutex);
123
    if (!m_index) return;
124

  
125
    std::cerr << "Generating index..." << std::endl;
126

  
127
    QDir composerDir;
128
    try {
129
	QString s = getComposerDirectoryName();
130
        composerDir = QDir(s);
131
    } catch (DirectoryCreationFailed f) {
132
        std::cerr << "ComposerFileIndex::updateIndex: ERROR: Failed to find or create composer directory: " << f.what() << std::endl;
133
        return;
134
    }
135

  
136
    composerDir.setFilter(QDir::Files);
137

  
138
    for (unsigned int i = 0; i < composerDir.count(); ++i) {
139
        QFileInfo fi(composerDir.filePath(composerDir[i]));
140
        if (fi.isFile() && fi.isReadable()) {
141
            index(QUrl::fromLocalFile(fi.filePath()));
142
        }
143
    }
144

  
145
    //!!! remove triples from index that refer to nonexistent files?
146

  
147
    std::cerr << "Saving index to " << m_indexFileName.toStdString() << std::endl;
148
    m_bs->save(m_indexFileName);
149

  
150
    std::cerr << "Done" << std::endl;
151
}
152

  
153
void
154
ComposerFileIndex::index(QUrl fileUrl)
155
{
156
    Triple typeTriple(Uri(fileUrl), "a", m_index->expand("foaf:Document"));
157

  
158
    if (m_index->contains(typeTriple)) {
159
        return;
160
    }
161

  
162
    Transaction *tx = m_index->startTransaction();
163
    tx->add(typeTriple);
164

  
165
    try {
166
        BasicStore *b = BasicStore::load(fileUrl);
167
        Triples ts = b->match
168
            (Triple(Node(), "a", m_index->expand("classical:Composer")));
169
        foreach (Triple t, ts) {
170
            tx->add(Triple(Uri(fileUrl), "foaf:primaryTopic", t.a));;
171
        }
172
    } catch (std::exception &e) {
173
        std::cerr << "Caught exception: \"" << e.what() << "\" while indexing "
174
                  << Uri(fileUrl) << ", skipping" << std::endl;
175
    }
176

  
177
    delete tx;
178
}
179

  
180

  
181
}
182

  
common/ComposerFileIndex.h
1
/* -*- c-basic-offset: 4 indent-tabs-mode: nil -*-  vi:set ts=8 sts=4 sw=4: */
2

  
3
#ifndef _CLASSICAL_DATA_COMPOSER_FILE_INDEX_H_
4
#define _CLASSICAL_DATA_COMPOSER_FILE_INDEX_H_
5

  
6
#include "Objects.h"
7

  
8
#include <dataquay/BasicStore.h>
9
#include <dataquay/TransactionalStore.h>
10

  
11
#include <QMutex>
12

  
13
namespace ClassicalData {
14

  
15
class ComposerFileIndex : public QObject
16
{
17
    Q_OBJECT
18

  
19
public:
20
    static ComposerFileIndex *getInstance();
21
    
22
    ComposerFileIndex();
23
    ~ComposerFileIndex();
24

  
25
    void loadFor(AudioFile *, Dataquay::Store *);
26

  
27
public slots:
28
    void composerFileAdded(QString filepath);
29

  
30
private:
31
    QMutex m_mutex;
32
    QString m_indexFileName;
33
    Dataquay::BasicStore *m_bs;
34
    Dataquay::TransactionalStore *m_index;
35
    QString getIndexFileName();
36
    QString getComposerDirectoryName();
37
    bool loadFor(Dataquay::Uri canonicalUri, Dataquay::Uri actingUri,
38
                 QString hash, Dataquay::Store *);
39
    void updateIndex();
40
    void index(QUrl);
41
};
42

  
43
}
44

  
45
#endif
46

  
47

  
48
    

Also available in: Unified diff